// Signature format: 2.0
package android.icu.text {

  public class DateFormatSymbols implements java.lang.Cloneable java.io.Serializable {
    ctor @Deprecated public DateFormatSymbols(android.icu.util.ULocale, String);
    method public String[] getNarrowEras();
  }

  public class DecimalFormat extends android.icu.text.NumberFormat {
    method public void setParseJavaCompatible(boolean);
  }

  public abstract class IDNA {
    method @Deprecated public static StringBuffer convertIDNToASCII(String, int) throws android.icu.text.StringPrepParseException;
    method @Deprecated public static StringBuffer convertIDNToUnicode(String, int) throws android.icu.text.StringPrepParseException;
  }

  public abstract class TimeZoneNames implements java.io.Serializable {
    method public java.util.Collection<android.icu.text.TimeZoneNames.MatchInfo> find(CharSequence, int, java.util.EnumSet<android.icu.text.TimeZoneNames.NameType>);
  }

  public static class TimeZoneNames.MatchInfo {
    method public int matchLength();
    method public String mzID();
    method public android.icu.text.TimeZoneNames.NameType nameType();
    method public String tzID();
  }

}

package android.icu.util {

  public class AnnualTimeZoneRule extends android.icu.util.TimeZoneRule {
    method public int getEndYear();
    method public android.icu.util.DateTimeRule getRule();
    field public static final int MAX_YEAR = 2147483647; // 0x7fffffff
  }

  public abstract class BasicTimeZone extends android.icu.util.TimeZone {
    method public abstract android.icu.util.TimeZoneTransition getNextTransition(long, boolean);
    method public abstract android.icu.util.TimeZoneTransition getPreviousTransition(long, boolean);
    method public abstract android.icu.util.TimeZoneRule[] getTimeZoneRules();
  }

  public abstract class Calendar implements java.lang.Cloneable java.lang.Comparable<android.icu.util.Calendar> java.io.Serializable {
    method public static String getDateTimeFormatString(android.icu.util.ULocale, String, int, int);
  }

  public class DateTimeRule implements java.io.Serializable {
    method public int getDateRuleType();
    method public int getRuleDayOfMonth();
    method public int getRuleDayOfWeek();
    method public int getRuleMillisInDay();
    method public int getRuleMonth();
    method public int getTimeRuleType();
    field public static final int DOM = 0; // 0x0
    field public static final int DOW = 1; // 0x1
    field public static final int DOW_GEQ_DOM = 2; // 0x2
    field public static final int DOW_LEQ_DOM = 3; // 0x3
    field public static final int STANDARD_TIME = 1; // 0x1
    field public static final int UTC_TIME = 2; // 0x2
    field public static final int WALL_TIME = 0; // 0x0
  }

  public class InitialTimeZoneRule extends android.icu.util.TimeZoneRule {
  }

  public abstract class TimeZone implements java.lang.Cloneable android.icu.util.Freezable<android.icu.util.TimeZone> java.io.Serializable {
    method @Deprecated public static void setICUDefault(android.icu.util.TimeZone);
  }

  public abstract class TimeZoneRule implements java.io.Serializable {
    method public int getDSTSavings();
    method public int getRawOffset();
  }

  public class TimeZoneTransition {
    method public android.icu.util.TimeZoneRule getFrom();
    method public long getTime();
    method public android.icu.util.TimeZoneRule getTo();
  }

  public final class ULocale implements java.lang.Comparable<android.icu.util.ULocale> java.io.Serializable {
    method @Deprecated public static String getRegionForSupplementalData(android.icu.util.ULocale, boolean);
  }

}

package com.android.i18n.system {

  public class AppSpecializationHooks {
    method public static void handleCompatChangesBeforeBindingApplication();
  }

  public final class ZygoteHooks {
    method public static void onBeginPreload();
    method public static void onEndPreload();
  }

}

package com.android.i18n.timezone {

  public final class ZoneInfoData {
    method public com.android.i18n.timezone.ZoneInfoData createCopyWithRawOffset(int);
    method public static com.android.i18n.timezone.ZoneInfoData createFromSerializationFields(String, java.io.ObjectInputStream.GetField) throws java.io.IOException;
    method public static com.android.i18n.timezone.ZoneInfoData createZoneInfo(String, java.nio.ByteBuffer) throws java.io.IOException;
    method public String getID();
    method public Integer getLatestDstSavings(long);
    method public int getOffset(long);
    method public int getOffsetsByUtcTime(long, int[]);
    method public int getRawOffset();
    method public long[] getTransitions();
    method public boolean hasSameRules(com.android.i18n.timezone.ZoneInfoData);
    method public boolean isInDaylightTime(long);
    method public void writeToSerializationFields(java.io.ObjectOutputStream.PutField);
    field public static final java.io.ObjectStreamField[] ZONEINFO_SERIALIZED_FIELDS;
  }

  public final class ZoneInfoDb {
    method public String[] getAvailableIDs();
    method public String[] getAvailableIDs(int);
    method public static com.android.i18n.timezone.ZoneInfoDb getInstance();
    method public com.android.i18n.timezone.ZoneInfoData makeZoneInfoData(String);
  }

}

package com.android.icu.charset {

  public final class CharsetICU extends java.nio.charset.Charset {
    method public static java.nio.charset.Charset charsetForName(String);
    method public static String[] getAvailableCharsetNames();
  }

}

package com.android.icu.text {

  public class DecimalFormatSymbolsBridge {
    method public static String getLocalizedPatternSeparator(android.icu.util.ULocale, android.icu.text.NumberingSystem);
  }

  public class ExtendedDateFormatSymbols {
    method public android.icu.text.DateFormatSymbols getDateFormatSymbols();
    method public static com.android.icu.text.ExtendedDateFormatSymbols getInstance(android.icu.util.ULocale);
    method public String[] getNarrowQuarters(int);
  }

  public final class TimeZoneNamesNative {
    method public static String[][] getFilledZoneStrings(@NonNull java.util.Locale, @NonNull String[]);
  }

}

package com.android.icu.util {

  public class CaseMapperNative {
    method public static String toLowerCase(String, java.util.Locale);
    method public static String toUpperCase(String, java.util.Locale);
  }

  public class Icu4cMetadata {
    method public static String getCldrVersion();
    method public static String getIcuVersion();
    method public static String getUnicodeVersion();
  }

  public final class LocaleNative {
    method public static String getDisplayCountry(java.util.Locale, java.util.Locale);
    method public static String getDisplayLanguage(java.util.Locale, java.util.Locale);
    method public static String getDisplayScript(java.util.Locale, java.util.Locale);
    method public static String getDisplayVariant(java.util.Locale, java.util.Locale);
    method public static void setDefault(String);
  }

}

package com.android.icu.util.regex {

  public class MatcherNative {
    method public static com.android.icu.util.regex.MatcherNative create(com.android.icu.util.regex.PatternNative);
    method public boolean find(int, int[]);
    method public boolean findNext(int[]);
    method public int getMatchedGroupIndex(String);
    method public int groupCount();
    method public boolean hitEnd();
    method public boolean lookingAt(int[]);
    method public boolean matches(int[]);
    method public boolean requireEnd();
    method public void setInput(String, int, int);
    method public void useAnchoringBounds(boolean);
    method public void useTransparentBounds(boolean);
  }

  public class PatternNative {
    method public static com.android.icu.util.regex.PatternNative create(String, int);
  }

}

