-//##header\r
-//#if defined(FOUNDATION10) || defined(J2SE13)\r
-//#else\r
-/*\r
- *******************************************************************************\r
- * Copyright (C) 2002-2009, International Business Machines Corporation and *\r
- * others. All Rights Reserved. *\r
- *******************************************************************************\r
- */\r
-package com.ibm.icu.dev.test.collator;\r
-\r
-\r
-import com.ibm.icu.text.Collator;\r
-import com.ibm.icu.text.RuleBasedCollator;\r
-import com.ibm.icu.text.UnicodeSet;\r
-\r
-import com.ibm.icu.dev.test.TestFmwk;\r
-import com.ibm.icu.dev.test.util.BNF;\r
-import com.ibm.icu.dev.test.util.BagFormatter;\r
-import com.ibm.icu.dev.test.util.Quoter;\r
-\r
-import java.io.File;\r
-import java.io.IOException;\r
-import java.io.PrintWriter;\r
-import java.text.ParseException;\r
-import java.util.Random;\r
-\r
-public class RandomCollator extends TestFmwk {\r
- public static void main(String[] args) throws Exception {\r
- new RandomCollator().run(args);\r
- //new CollationAPITest().TestGetTailoredSet();\r
- }\r
-\r
- static final int CONSTRUCT_RANDOM_COUNT = 100;\r
- static final int FORMAL_TEST_COUNT = 1000;\r
- \r
- static final String POSITION = "{$$$}";\r
- \r
- /*\r
- class Shower extends BagFormatter.Shower {\r
- public void print(String arg) {\r
- log(arg);\r
- }\r
- }\r
- \r
- public Shower LOG = new Shower();\r
- */\r
- \r
- public void TestRandom() throws IOException {\r
-// int year \r
-// = java.util.Calendar.getInstance().get(java.util.Calendar.YEAR);\r
-// if (year < 2004) {\r
-// System.out.println("\nTestRandom skipped for 2003");\r
-// return;\r
-// }\r
- //String fileName;\r
- PrintWriter pw = BagFormatter.openUTF8Writer(System.getProperty("user.dir")+File.separator, "RandomCollationTestLog.txt");\r
- TestCollator tc = new TestCollator(chars);\r
- pw.println("Collation Test Run");\r
- pw.println("Note: For parse-exception, " + POSITION + " indicates the errorOffset");\r
- pw.println("Rules:");\r
- pw.println(currentRules);\r
- String rules = "<unknown>";\r
- int sCount = 0;\r
- int peCount = 0;\r
- int oeCount = 0;\r
- for (int i = 0; i < CONSTRUCT_RANDOM_COUNT; ++i) {\r
- try {\r
- rules = get();\r
- if (true) { \r
- Collator c = new RuleBasedCollator(rules.toString());\r
- tc.test(c, FORMAL_TEST_COUNT);\r
- } else {\r
- pw.println(rules);\r
- }\r
- logln("ok");\r
- sCount++;\r
- } catch (ParseException pe) {\r
- peCount++;\r
- pw.println("========PARSE EXCEPTION======== (" + i + ")");\r
- int errorOffset = pe.getErrorOffset();\r
- pw.print(rules.substring(0,errorOffset));\r
- pw.print(POSITION);\r
- pw.println(rules.substring(errorOffset));\r
- //pw.println("========ERROR======== (" + i + ")");\r
- //pe.printStackTrace(pw);\r
- //pw.println("========END======== (" + i + ")");\r
- errln("ParseException");\r
- } catch (Exception e) {\r
- oeCount++;\r
- pw.println("========OTHER EXCEPTION======== (" + i + ")");\r
- e.printStackTrace(pw);\r
- pw.println("========RULES======== (" + i + ")");\r
- pw.println(rules);\r
- //pw.println("========END======== (" + i + ")");\r
- errln("ParseException");\r
- }\r
- }\r
- pw.println("Successful: " + sCount \r
- + ",\tParseException: " + peCount \r
- + ",\tOther Exception: " + oeCount);\r
- logln("Successful: " + sCount \r
- + ",\tParseException: " + peCount \r
- + ",\tOther Exception: " + oeCount);\r
- pw.close();\r
-\r
- }\r
- \r
- public static class TestCollator extends TestComparator {\r
- BNF rs;\r
- \r
- TestCollator(UnicodeSet chars) {\r
- rs = new BNF(new Random(0), new Quoter.RuleQuoter())\r
- .addRules("$root = " + chars + "{1,8};").complete();\r
- }\r
- \r
- public Object newObject(Object c) {\r
- return rs.next();\r
- }\r
- \r
- public String format(Object c) {\r
- return BagFormatter.hex.transliterate(c.toString());\r
- }\r
- }\r
-\r
- private BNF bnf;\r
- String currentRules = null;\r
- UnicodeSet chars;\r
- \r
- public String get() {\r
- return bnf.next();\r
- }\r
- \r
- public RandomCollator() {\r
- \r
- }\r
- protected void init()throws Exception{\r
- init(1,10, new UnicodeSet("[AZa-z<\\&\\[\\]]"));\r
- }\r
- private void init(int minRuleCount, int maxRuleCount, UnicodeSet setOfChars) {\r
- this.chars = setOfChars;\r
- bnf = new BNF(new Random(0), new Quoter.RuleQuoter())\r
- .addSet("$chars", setOfChars)\r
- .addRules(collationBNF)\r
- .complete();\r
- }\r
- \r
- private static String collationBNF =\r
- "$s = ' '? 50%;\r\n" +\r
- "$relationList = (" + " '<'" + " | ' <<'" + " | ' ;'" +\r
- " | ' <<<'" + " | ' ,'" +\r
- " | ' ='" + ");\r\n" +\r
- "$alternateOptions = non'-'ignorable | shifted;\r\n" +\r
- "$caseFirstOptions = off | upper | lower;\r\n" +\r
- "$strengthOptions = '1' | '2' | '3' | '4' | 'I';\r\n" +\r
- "$commandList = '['" + " ( alternate ' ' $alternateOptions" + " | backwards' 2'" + " | normalization ' ' $onoff " + " | caseLevel ' ' $onoff " + " | hiraganaQ ' ' $onoff" + " | caseFirst ' ' $caseFirstOptions" + " | strength ' ' $strengthOptions" + " ) ']';\r\n" +\r
- "$ignorableTypes = (tertiary | secondary | primary) ' ' ignorable;\r\n" +\r
- "$allTypes = variable | regular | implicit | trailing | $ignorableTypes;\r\n" +\r
- "$onoff = on | off;\r\n" +\r
- "$positionList = '[' (first | last) ' ' $allTypes ']';\r\n" + "$beforeList = '[before ' ('1' | '2' | '3') ']';\r\n" + "$string = $chars{1,5}~@;\r\n" +\r
- "$crlf = '\r\n';\r\n" +\r
- "$rel1 = '[variable top]' $s ;\r\n" +\r
- "$p1 = ($string $s '|' $s)? 25%;\r\n" +\r
- "$p2 = ('\\' $s $string $s)? 25%;\r\n" +\r
- "$rel2 = $p1 $string $s $p2;\r\n" +\r
- "$relation = $relationList $s ($rel1 | $rel2) $crlf;\r\n" +\r
- "$command = $commandList $crlf;\r\n" +\r
- "$reset = '&' $s ($beforeList $s)? 10% ($positionList | $string 10%) $crlf;\r\n" +\r
- "$mostRules = $command 1% | $reset 5% | $relation 25%;\r\n" +\r
- "$root = $command{0,5} $reset $mostRules{1,20};\r\n";\r
- \r
- \r
-/* \r
- \r
- \r
- gc ; C ; Other # Cc | Cf | Cn | Co | Cs\r
- gc ; Cc ; Control\r
- gc ; Cf ; Format\r
- gc ; Cn ; Unassigned\r
- gc ; Co ; Private_Use\r
- gc ; Cs ; Surrogate\r
- gc ; L ; Letter # Ll | Lm | Lo | Lt | Lu\r
- gc ; LC ; Cased_Letter # Ll | Lt | Lu\r
- gc ; Ll ; Lowercase_Letter\r
- gc ; Lm ; Modifier_Letter\r
- gc ; Lo ; Other_Letter\r
- gc ; Lt ; Titlecase_Letter\r
- gc ; Lu ; Uppercase_Letter\r
- gc ; M ; Mark # Mc | Me | Mn\r
- gc ; Mc ; Spacing_Mark\r
- gc ; Me ; Enclosing_Mark\r
- gc ; Mn ; Nonspacing_Mark\r
- gc ; N ; Number # Nd | Nl | No\r
- gc ; Nd ; Decimal_Number\r
- gc ; Nl ; Letter_Number\r
- gc ; No ; Other_Number\r
- gc ; P ; Punctuation # Pc | Pd | Pe | Pf | Pi | Po | Ps\r
- gc ; Pc ; Connector_Punctuation\r
- gc ; Pd ; Dash_Punctuation\r
- gc ; Pe ; Close_Punctuation\r
- gc ; Pf ; Final_Punctuation\r
- gc ; Pi ; Initial_Punctuation\r
- gc ; Po ; Other_Punctuation\r
- gc ; Ps ; Open_Punctuation\r
- gc ; S ; Symbol # Sc | Sk | Sm | So\r
- gc ; Sc ; Currency_Symbol\r
- gc ; Sk ; Modifier_Symbol\r
- gc ; Sm ; Math_Symbol\r
- gc ; So ; Other_Symbol\r
- gc ; Z ; Separator # Zl | Zp | Zs\r
- gc ; Zl ; Line_Separator\r
- gc ; Zp ; Paragraph_Separator\r
- gc ; Zs ; Space_Separator\r
-*/\r
-\r
- /*\r
- // each rule can be:\r
- // "[" command "]"\r
- // "& [" position "]"\r
- // "&" before chars\r
- // relation "[variable top]"\r
- // relation (chars "|")? chars ("/" chars)?\r
- // plus, a reset must come before a relation\r
- \r
- // the following reflects the above rules, plus allows whitespace.\r
- Pick chars = Pick.string(1, 5, Pick.codePoint(uSet)); // insert something needing quotes\r
- Pick s = Pick.maybe(0.8, Pick.unquoted(" ")).name("Space"); // optional space\r
- Pick CRLF = Pick.unquoted("\r\n");\r
- \r
- Pick rel1 = Pick.and(Pick.unquoted("[variable top]")).and2(s);\r
- Pick p1 = Pick.maybe(0.25, Pick.and(chars).and2(s).and2("|").and2(s));\r
- Pick p2 = Pick.maybe(0.25, Pick.and("/").and2(s).and2(chars).and2(s));\r
- Pick rel2 = Pick.and(p1).and2(chars).and2(s).and2(p2);\r
- Pick relation = Pick.and(Pick.or(relationList)).and2(s)\r
- .and2(Pick.or(1, rel1).or2(10, rel2))\r
- .and2(CRLF).name("Relation");\r
- \r
- Pick command = Pick.and(Pick.or(commandList)).and2(CRLF).name("Command");\r
- \r
- Pick reset = Pick.and("&").and2(s) \r
- .and2(0.1, Pick.or(beforeList)).and2(s) \r
- .and2(Pick.or(0.1, Pick.or(positionList)).or2(1.0, chars))\r
- .and2(CRLF).name("Reset");\r
- Pick rule = Pick.and(Pick.or(1, command).or2(5, reset).or2(25, relation)).name("Rule");\r
- Pick rules2 = Pick.and(Pick.repeat(0,5,command)) \r
- .and2(reset) \r
- .and2(Pick.repeat(1,20,rule)).name("Rules");\r
- rules = Pick.Target.make(rules2);\r
- \r
- static final String[] relationList = {" <", " <<", " <<<", " =", " ;", " ,"};\r
- \r
- static final String[] commandList = {\r
- "[alternate non-ignorable]", "[alternate shifted]",\r
- "[backwards 2]",\r
- "[normalization off]",\r
- "[normalization on]",\r
- "[caseLevel off]",\r
- "[caseLevel on]",\r
- "[caseFirst off]",\r
- "[caseFirst upper]",\r
- "[caseFirst lower]",\r
- "[strength 1]",\r
- "[strength 2]",\r
- "[strength 3]",\r
- "[strength 4]",\r
- "[strength I]",\r
- "[hiraganaQ off]",\r
- "[hiraganaQ on]"\r
- };\r
- \r
- static final String[] positionList = {\r
- "[first tertiary ignorable]",\r
- "[last tertiary ignorable]",\r
- "[first secondary ignorable]",\r
- "[last secondary ignorable]",\r
- "[first primary ignorable]",\r
- "[last primary ignorable]",\r
- "[first variable]",\r
- "[last variable]",\r
- "[first regular]",\r
- "[last regular]",\r
- "[first implicit]",\r
- "[last implicit]",\r
- "[first trailing]",\r
- "[last trailing]"\r
- };\r
- \r
- static final String[] beforeList = {\r
- "[before 1]", \r
- "[before 2]",\r
- "[before 3]"\r
- };\r
- */\r
-}\r
-//#endif\r
-\r
+//##header J2SE15
+//#if defined(FOUNDATION10) || defined(J2SE13)
+//#else
+/*
+ *******************************************************************************
+ * Copyright (C) 2002-2009, International Business Machines Corporation and *
+ * others. All Rights Reserved. *
+ *******************************************************************************
+ */
+package com.ibm.icu.dev.test.collator;
+
+
+import com.ibm.icu.text.Collator;
+import com.ibm.icu.text.RuleBasedCollator;
+import com.ibm.icu.text.UnicodeSet;
+
+import com.ibm.icu.dev.test.TestFmwk;
+import com.ibm.icu.dev.test.util.BNF;
+import com.ibm.icu.dev.test.util.BagFormatter;
+import com.ibm.icu.dev.test.util.Quoter;
+
+import java.io.File;
+import java.io.IOException;
+import java.io.PrintWriter;
+import java.text.ParseException;
+import java.util.Random;
+
+public class RandomCollator extends TestFmwk {
+ public static void main(String[] args) throws Exception {
+ new RandomCollator().run(args);
+ //new CollationAPITest().TestGetTailoredSet();
+ }
+
+ static final int CONSTRUCT_RANDOM_COUNT = 100;
+ static final int FORMAL_TEST_COUNT = 1000;
+
+ static final String POSITION = "{$$$}";
+
+ /*
+ class Shower extends BagFormatter.Shower {
+ public void print(String arg) {
+ log(arg);
+ }
+ }
+
+ public Shower LOG = new Shower();
+ */
+
+ public void TestRandom() throws IOException {
+// int year
+// = java.util.Calendar.getInstance().get(java.util.Calendar.YEAR);
+// if (year < 2004) {
+// System.out.println("\nTestRandom skipped for 2003");
+// return;
+// }
+ //String fileName;
+ PrintWriter pw = BagFormatter.openUTF8Writer(System.getProperty("user.dir")+File.separator, "RandomCollationTestLog.txt");
+ TestCollator tc = new TestCollator(chars);
+ pw.println("Collation Test Run");
+ pw.println("Note: For parse-exception, " + POSITION + " indicates the errorOffset");
+ pw.println("Rules:");
+ pw.println(currentRules);
+ String rules = "<unknown>";
+ int sCount = 0;
+ int peCount = 0;
+ int oeCount = 0;
+ for (int i = 0; i < CONSTRUCT_RANDOM_COUNT; ++i) {
+ try {
+ rules = get();
+ if (true) {
+ Collator c = new RuleBasedCollator(rules.toString());
+ tc.test(c, FORMAL_TEST_COUNT);
+ } else {
+ pw.println(rules);
+ }
+ logln("ok");
+ sCount++;
+ } catch (ParseException pe) {
+ peCount++;
+ pw.println("========PARSE EXCEPTION======== (" + i + ")");
+ int errorOffset = pe.getErrorOffset();
+ pw.print(rules.substring(0,errorOffset));
+ pw.print(POSITION);
+ pw.println(rules.substring(errorOffset));
+ //pw.println("========ERROR======== (" + i + ")");
+ //pe.printStackTrace(pw);
+ //pw.println("========END======== (" + i + ")");
+ errln("ParseException");
+ } catch (Exception e) {
+ oeCount++;
+ pw.println("========OTHER EXCEPTION======== (" + i + ")");
+ e.printStackTrace(pw);
+ pw.println("========RULES======== (" + i + ")");
+ pw.println(rules);
+ //pw.println("========END======== (" + i + ")");
+ errln("ParseException");
+ }
+ }
+ pw.println("Successful: " + sCount
+ + ",\tParseException: " + peCount
+ + ",\tOther Exception: " + oeCount);
+ logln("Successful: " + sCount
+ + ",\tParseException: " + peCount
+ + ",\tOther Exception: " + oeCount);
+ pw.close();
+
+ }
+
+ public static class TestCollator extends TestComparator {
+ BNF rs;
+
+ TestCollator(UnicodeSet chars) {
+ rs = new BNF(new Random(0), new Quoter.RuleQuoter())
+ .addRules("$root = " + chars + "{1,8};").complete();
+ }
+
+ public Object newObject(Object c) {
+ return rs.next();
+ }
+
+ public String format(Object c) {
+ return BagFormatter.hex.transliterate(c.toString());
+ }
+ }
+
+ private BNF bnf;
+ String currentRules = null;
+ UnicodeSet chars;
+
+ public String get() {
+ return bnf.next();
+ }
+
+ public RandomCollator() {
+
+ }
+ protected void init()throws Exception{
+ init(1,10, new UnicodeSet("[AZa-z<\\&\\[\\]]"));
+ }
+ private void init(int minRuleCount, int maxRuleCount, UnicodeSet setOfChars) {
+ this.chars = setOfChars;
+ bnf = new BNF(new Random(0), new Quoter.RuleQuoter())
+ .addSet("$chars", setOfChars)
+ .addRules(collationBNF)
+ .complete();
+ }
+
+ private static String collationBNF =
+ "$s = ' '? 50%;\r\n" +
+ "$relationList = (" + " '<'" + " | ' <<'" + " | ' ;'" +
+ " | ' <<<'" + " | ' ,'" +
+ " | ' ='" + ");\r\n" +
+ "$alternateOptions = non'-'ignorable | shifted;\r\n" +
+ "$caseFirstOptions = off | upper | lower;\r\n" +
+ "$strengthOptions = '1' | '2' | '3' | '4' | 'I';\r\n" +
+ "$commandList = '['" + " ( alternate ' ' $alternateOptions" + " | backwards' 2'" + " | normalization ' ' $onoff " + " | caseLevel ' ' $onoff " + " | hiraganaQ ' ' $onoff" + " | caseFirst ' ' $caseFirstOptions" + " | strength ' ' $strengthOptions" + " ) ']';\r\n" +
+ "$ignorableTypes = (tertiary | secondary | primary) ' ' ignorable;\r\n" +
+ "$allTypes = variable | regular | implicit | trailing | $ignorableTypes;\r\n" +
+ "$onoff = on | off;\r\n" +
+ "$positionList = '[' (first | last) ' ' $allTypes ']';\r\n" + "$beforeList = '[before ' ('1' | '2' | '3') ']';\r\n" + "$string = $chars{1,5}~@;\r\n" +
+ "$crlf = '\r\n';\r\n" +
+ "$rel1 = '[variable top]' $s ;\r\n" +
+ "$p1 = ($string $s '|' $s)? 25%;\r\n" +
+ "$p2 = ('\\' $s $string $s)? 25%;\r\n" +
+ "$rel2 = $p1 $string $s $p2;\r\n" +
+ "$relation = $relationList $s ($rel1 | $rel2) $crlf;\r\n" +
+ "$command = $commandList $crlf;\r\n" +
+ "$reset = '&' $s ($beforeList $s)? 10% ($positionList | $string 10%) $crlf;\r\n" +
+ "$mostRules = $command 1% | $reset 5% | $relation 25%;\r\n" +
+ "$root = $command{0,5} $reset $mostRules{1,20};\r\n";
+
+
+/*
+
+
+ gc ; C ; Other # Cc | Cf | Cn | Co | Cs
+ gc ; Cc ; Control
+ gc ; Cf ; Format
+ gc ; Cn ; Unassigned
+ gc ; Co ; Private_Use
+ gc ; Cs ; Surrogate
+ gc ; L ; Letter # Ll | Lm | Lo | Lt | Lu
+ gc ; LC ; Cased_Letter # Ll | Lt | Lu
+ gc ; Ll ; Lowercase_Letter
+ gc ; Lm ; Modifier_Letter
+ gc ; Lo ; Other_Letter
+ gc ; Lt ; Titlecase_Letter
+ gc ; Lu ; Uppercase_Letter
+ gc ; M ; Mark # Mc | Me | Mn
+ gc ; Mc ; Spacing_Mark
+ gc ; Me ; Enclosing_Mark
+ gc ; Mn ; Nonspacing_Mark
+ gc ; N ; Number # Nd | Nl | No
+ gc ; Nd ; Decimal_Number
+ gc ; Nl ; Letter_Number
+ gc ; No ; Other_Number
+ gc ; P ; Punctuation # Pc | Pd | Pe | Pf | Pi | Po | Ps
+ gc ; Pc ; Connector_Punctuation
+ gc ; Pd ; Dash_Punctuation
+ gc ; Pe ; Close_Punctuation
+ gc ; Pf ; Final_Punctuation
+ gc ; Pi ; Initial_Punctuation
+ gc ; Po ; Other_Punctuation
+ gc ; Ps ; Open_Punctuation
+ gc ; S ; Symbol # Sc | Sk | Sm | So
+ gc ; Sc ; Currency_Symbol
+ gc ; Sk ; Modifier_Symbol
+ gc ; Sm ; Math_Symbol
+ gc ; So ; Other_Symbol
+ gc ; Z ; Separator # Zl | Zp | Zs
+ gc ; Zl ; Line_Separator
+ gc ; Zp ; Paragraph_Separator
+ gc ; Zs ; Space_Separator
+*/
+
+ /*
+ // each rule can be:
+ // "[" command "]"
+ // "& [" position "]"
+ // "&" before chars
+ // relation "[variable top]"
+ // relation (chars "|")? chars ("/" chars)?
+ // plus, a reset must come before a relation
+
+ // the following reflects the above rules, plus allows whitespace.
+ Pick chars = Pick.string(1, 5, Pick.codePoint(uSet)); // insert something needing quotes
+ Pick s = Pick.maybe(0.8, Pick.unquoted(" ")).name("Space"); // optional space
+ Pick CRLF = Pick.unquoted("\r\n");
+
+ Pick rel1 = Pick.and(Pick.unquoted("[variable top]")).and2(s);
+ Pick p1 = Pick.maybe(0.25, Pick.and(chars).and2(s).and2("|").and2(s));
+ Pick p2 = Pick.maybe(0.25, Pick.and("/").and2(s).and2(chars).and2(s));
+ Pick rel2 = Pick.and(p1).and2(chars).and2(s).and2(p2);
+ Pick relation = Pick.and(Pick.or(relationList)).and2(s)
+ .and2(Pick.or(1, rel1).or2(10, rel2))
+ .and2(CRLF).name("Relation");
+
+ Pick command = Pick.and(Pick.or(commandList)).and2(CRLF).name("Command");
+
+ Pick reset = Pick.and("&").and2(s)
+ .and2(0.1, Pick.or(beforeList)).and2(s)
+ .and2(Pick.or(0.1, Pick.or(positionList)).or2(1.0, chars))
+ .and2(CRLF).name("Reset");
+ Pick rule = Pick.and(Pick.or(1, command).or2(5, reset).or2(25, relation)).name("Rule");
+ Pick rules2 = Pick.and(Pick.repeat(0,5,command))
+ .and2(reset)
+ .and2(Pick.repeat(1,20,rule)).name("Rules");
+ rules = Pick.Target.make(rules2);
+
+ static final String[] relationList = {" <", " <<", " <<<", " =", " ;", " ,"};
+
+ static final String[] commandList = {
+ "[alternate non-ignorable]", "[alternate shifted]",
+ "[backwards 2]",
+ "[normalization off]",
+ "[normalization on]",
+ "[caseLevel off]",
+ "[caseLevel on]",
+ "[caseFirst off]",
+ "[caseFirst upper]",
+ "[caseFirst lower]",
+ "[strength 1]",
+ "[strength 2]",
+ "[strength 3]",
+ "[strength 4]",
+ "[strength I]",
+ "[hiraganaQ off]",
+ "[hiraganaQ on]"
+ };
+
+ static final String[] positionList = {
+ "[first tertiary ignorable]",
+ "[last tertiary ignorable]",
+ "[first secondary ignorable]",
+ "[last secondary ignorable]",
+ "[first primary ignorable]",
+ "[last primary ignorable]",
+ "[first variable]",
+ "[last variable]",
+ "[first regular]",
+ "[last regular]",
+ "[first implicit]",
+ "[last implicit]",
+ "[first trailing]",
+ "[last trailing]"
+ };
+
+ static final String[] beforeList = {
+ "[before 1]",
+ "[before 2]",
+ "[before 3]"
+ };
+ */
+}
+//#endif
+