1 /********************************************************************
3 * Copyright (c) 1997-2006, International Business Machines Corporation and
4 * others. All Rights Reserved.
5 ********************************************************************/
6 //===============================================================================
12 // Created by: Helena Shih
14 // Modification History:
16 // Date Name Description
17 // 2/5/97 aliu Added streamIn and streamOut methods. Added
18 // constructor which reads RuleBasedCollator object from
19 // a binary file. Added writeToFile method which streams
20 // RuleBasedCollator out to a binary file. The streamIn
21 // and streamOut methods use istream and ostream objects
23 // 6/30/97 helena Added tests for CollationElementIterator::setText, getOffset
24 // setOffset and DecompositionIterator::getOffset, setOffset.
25 // DecompositionIterator is made public so add class scope
27 // 02/10/98 damiba Added test for compare(UnicodeString&, UnicodeString&, int32_t)
28 //===============================================================================
30 #include "unicode/utypes.h"
32 #if !UCONFIG_NO_COLLATION
34 #include "unicode/coll.h"
35 #include "unicode/tblcoll.h"
36 #include "unicode/coleitr.h"
37 #include "unicode/sortkey.h"
39 #include "unicode/chariter.h"
40 #include "unicode/schriter.h"
41 #include "unicode/ustring.h"
42 #include "unicode/ucol.h"
49 CollationAPITest::doAssert(UBool condition
, const char *message
)
52 errln(UnicodeString("ERROR : ") + message
);
56 #ifdef U_USE_COLLATION_OBSOLETE_2_6
58 * Test Collator::createInstance(... version...) for some locale. Called by TestProperty().
61 TestOpenVersion(IntlTest
&test
, const Locale
&locale
) {
62 UVersionInfo version1
, version2
;
63 Collator
*collator1
, *collator2
;
66 errorCode
=U_ZERO_ERROR
;
67 collator1
=Collator::createInstance(locale
, errorCode
);
68 if(U_SUCCESS(errorCode
)) {
69 /* get the current version */
70 collator1
->getVersion(version1
);
73 /* try to get that same version again */
74 collator2
=Collator::createInstance(locale
, version1
, errorCode
);
75 if(U_SUCCESS(errorCode
)) {
76 collator2
->getVersion(version2
);
77 if(0!=uprv_memcmp(version1
, version2
, sizeof(UVersionInfo
))) {
78 test
.errln("error: Collator::createInstance(\"%s\", (%s collator)->getVersion()) returns a different collator\n", locale
.getName(), locale
.getName());
82 test
.errln("error: Collator::createInstance(\"%s\", (%s collator)->getVersion()) fails: %s\n", locale
.getName(), locale
.getName(), u_errorName(errorCode
));
88 // Collator Class Properties
89 // ctor, dtor, createInstance, compare, getStrength/setStrength
90 // getDecomposition/setDecomposition, getDisplayName
92 CollationAPITest::TestProperty(/* char* par */)
94 UErrorCode success
= U_ZERO_ERROR
;
97 All the collations have the same version in an ICU
99 ICU 2.0 currVersionArray = {0x18, 0xC0, 0x02, 0x02};
100 ICU 2.1 currVersionArray = {0x19, 0x00, 0x03, 0x03};
101 ICU 2.2 currVersionArray = {0x21, 0x40, 0x04, 0x04};
102 ICU 2.4 currVersionArray = {0x21, 0x40, 0x04, 0x04};
103 ICU 2.6 currVersionArray = {0x21, 0x40, 0x03, 0x03};
104 ICU 2.8 currVersionArray = {0x29, 0x80, 0x00, 0x04};
105 ICU 3.4 currVersionArray = {0x31, 0xC0, 0x00, 0x04};
107 UVersionInfo currVersionArray
= {0x31, 0xC0, 0x00, 0x05};
108 UVersionInfo versionArray
;
111 logln("The property tests begin : ");
112 logln("Test ctors : ");
113 col
= Collator::createInstance(Locale::getEnglish(), success
);
115 if (U_FAILURE(success
))
117 errln("Default Collator creation failed.");
121 col
->getVersion(versionArray
);
122 for (i
=0; i
<4; ++i
) {
123 if (versionArray
[i
] != currVersionArray
[i
]) {
124 errln("Testing ucol_getVersion() - unexpected result: %d.%d.%d.%d",
125 versionArray
[0], versionArray
[1], versionArray
[2], versionArray
[3]);
130 doAssert((col
->compare("ab", "abc") == Collator::LESS
), "ab < abc comparison failed");
131 doAssert((col
->compare("ab", "AB") == Collator::LESS
), "ab < AB comparison failed");
132 doAssert((col
->compare("blackbird", "black-bird") == Collator::GREATER
), "black-bird > blackbird comparison failed");
133 doAssert((col
->compare("black bird", "black-bird") == Collator::LESS
), "black bird > black-bird comparison failed");
134 doAssert((col
->compare("Hello", "hello") == Collator::GREATER
), "Hello > hello comparison failed");
137 /*start of update [Bertrand A. D. 02/10/98]*/
138 doAssert((col
->compare("ab", "abc", 2) == Collator::EQUAL
), "ab = abc with length 2 comparison failed");
139 doAssert((col
->compare("ab", "AB", 2) == Collator::LESS
), "ab < AB with length 2 comparison failed");
140 doAssert((col
->compare("ab", "Aa", 1) == Collator::LESS
), "ab < Aa with length 1 comparison failed");
141 doAssert((col
->compare("ab", "Aa", 2) == Collator::GREATER
), "ab > Aa with length 2 comparison failed");
142 doAssert((col
->compare("black-bird", "blackbird", 5) == Collator::EQUAL
), "black-bird = blackbird with length of 5 comparison failed");
143 doAssert((col
->compare("black bird", "black-bird", 10) == Collator::LESS
), "black bird < black-bird with length 10 comparison failed");
144 doAssert((col
->compare("Hello", "hello", 5) == Collator::GREATER
), "Hello > hello with length 5 comparison failed");
145 /*end of update [Bertrand A. D. 02/10/98]*/
148 logln("Test ctors ends.");
149 logln("testing Collator::getStrength() method ...");
150 doAssert((col
->getStrength() == Collator::TERTIARY
), "collation object has the wrong strength");
151 doAssert((col
->getStrength() != Collator::PRIMARY
), "collation object's strength is primary difference");
154 logln("testing Collator::setStrength() method ...");
155 col
->setStrength(Collator::SECONDARY
);
156 doAssert((col
->getStrength() != Collator::TERTIARY
), "collation object's strength is secondary difference");
157 doAssert((col
->getStrength() != Collator::PRIMARY
), "collation object's strength is primary difference");
158 doAssert((col
->getStrength() == Collator::SECONDARY
), "collation object has the wrong strength");
162 logln("Get display name for the US English collation in German : ");
163 logln(Collator::getDisplayName(Locale::getUS(), Locale::getGerman(), name
));
164 doAssert((name
== UnicodeString("Englisch (Vereinigte Staaten)")), "getDisplayName failed");
166 logln("Get display name for the US English collation in English : ");
167 logln(Collator::getDisplayName(Locale::getUS(), Locale::getEnglish(), name
));
168 doAssert((name
== UnicodeString("English (United States)")), "getDisplayName failed");
170 // weiv : this test is bogus if we're running on any machine that has different default locale than English.
171 // Therefore, it is banned!
172 logln("Get display name for the US English in default locale language : ");
173 logln(Collator::getDisplayName(Locale::US
, name
));
174 doAssert((name
== UnicodeString("English (United States)")), "getDisplayName failed if this is an English machine");
177 RuleBasedCollator
*rcol
= (RuleBasedCollator
*)Collator::createInstance("da_DK",
179 doAssert(rcol
->getRules().length() != 0, "da_DK rules does not have length 0");
182 col
= Collator::createInstance(Locale::getFrench(), success
);
183 if (U_FAILURE(success
))
185 errln("Creating French collation failed.");
189 col
->setStrength(Collator::PRIMARY
);
190 logln("testing Collator::getStrength() method again ...");
191 doAssert((col
->getStrength() != Collator::TERTIARY
), "collation object has the wrong strength");
192 doAssert((col
->getStrength() == Collator::PRIMARY
), "collation object's strength is not primary difference");
194 logln("testing French Collator::setStrength() method ...");
195 col
->setStrength(Collator::TERTIARY
);
196 doAssert((col
->getStrength() == Collator::TERTIARY
), "collation object's strength is not tertiary difference");
197 doAssert((col
->getStrength() != Collator::PRIMARY
), "collation object's strength is primary difference");
198 doAssert((col
->getStrength() != Collator::SECONDARY
), "collation object's strength is secondary difference");
200 logln("Create junk collation: ");
201 Locale
abcd("ab", "CD", "");
202 success
= U_ZERO_ERROR
;
204 junk
= Collator::createInstance(abcd
, success
);
206 if (U_FAILURE(success
))
208 errln("Junk collation creation failed, should at least return default.");
214 col
= Collator::createInstance(success
);
215 if (U_FAILURE(success
))
217 errln("Creating default collator failed.");
222 doAssert(((RuleBasedCollator
*)col
)->getRules() == ((RuleBasedCollator
*)junk
)->getRules(),
223 "The default collation should be returned.");
224 Collator
*frCol
= Collator::createInstance(Locale::getFrance(), success
);
225 if (U_FAILURE(success
))
227 errln("Creating French collator failed.");
228 delete col
; delete junk
;
232 doAssert((*frCol
!= *junk
), "The junk is the same as the French collator.");
233 Collator
*aFrCol
= frCol
->clone();
234 doAssert((*frCol
== *aFrCol
), "The cloning of a French collator failed.");
235 logln("Collator property test ended.");
242 #ifdef U_USE_COLLATION_OBSOLETE_2_6
243 /* test Collator::createInstance(...version...) */
244 TestOpenVersion(*this, "");
245 TestOpenVersion(*this, "da");
246 TestOpenVersion(*this, "fr");
247 TestOpenVersion(*this, "ja");
249 /* try some bogus version */
251 versionArray
[1]=0x99;
252 versionArray
[2]=0xc7;
253 versionArray
[3]=0xfe;
254 col
=Collator::createInstance(Locale(), versionArray
, success
);
255 if(U_SUCCESS(success
)) {
256 errln("error: ucol_openVersion(bogus version) succeeded");
263 CollationAPITest::TestRuleBasedColl()
265 RuleBasedCollator
*col1
, *col2
, *col3
, *col4
;
266 UErrorCode status
= U_ZERO_ERROR
;
268 UnicodeString
ruleset1("&9 < a, A < b, B < c, C; ch, cH, Ch, CH < d, D, e, E");
269 UnicodeString
ruleset2("&9 < a, A < b, B < c, C < d, D, e, E");
271 col1
= new RuleBasedCollator(ruleset1
, status
);
272 if (U_FAILURE(status
)) {
273 errln("RuleBased Collator creation failed.\n");
277 logln("PASS: RuleBased Collator creation passed\n");
280 status
= U_ZERO_ERROR
;
281 col2
= new RuleBasedCollator(ruleset2
, status
);
282 if (U_FAILURE(status
)) {
283 errln("RuleBased Collator creation failed.\n");
287 logln("PASS: RuleBased Collator creation passed\n");
290 status
= U_ZERO_ERROR
;
291 Locale
locale("aa", "AA");
292 col3
= (RuleBasedCollator
*)Collator::createInstance(locale
, status
);
293 if (U_FAILURE(status
)) {
294 errln("Fallback Collator creation failed.: %s\n");
298 logln("PASS: Fallback Collator creation passed\n");
302 status
= U_ZERO_ERROR
;
303 col3
= (RuleBasedCollator
*)Collator::createInstance(status
);
304 if (U_FAILURE(status
)) {
305 errln("Default Collator creation failed.: %s\n");
309 logln("PASS: Default Collator creation passed\n");
312 UnicodeString rule1
= col1
->getRules();
313 UnicodeString rule2
= col2
->getRules();
314 UnicodeString rule3
= col3
->getRules();
316 doAssert(rule1
!= rule2
, "Default collator getRules failed");
317 doAssert(rule2
!= rule3
, "Default collator getRules failed");
318 doAssert(rule1
!= rule3
, "Default collator getRules failed");
320 col4
= new RuleBasedCollator(rule2
, status
);
321 if (U_FAILURE(status
)) {
322 errln("RuleBased Collator creation failed.\n");
326 UnicodeString rule4
= col4
->getRules();
327 doAssert(rule2
== rule4
, "Default collator getRules failed");
329 uint8_t *clonedrule4
= col4
->cloneRuleData(length4
, status
);
330 if (U_FAILURE(status
)) {
331 errln("Cloned rule data failed.\n");
335 // free(clonedrule4); BAD API!!!!
336 uprv_free(clonedrule4
);
346 CollationAPITest::TestRules()
348 RuleBasedCollator
*coll
;
349 UErrorCode status
= U_ZERO_ERROR
;
352 coll
= (RuleBasedCollator
*)Collator::createInstance(Locale::getEnglish(), status
);
353 if (U_FAILURE(status
)) {
354 errln("English Collator creation failed.\n");
358 logln("PASS: RuleBased Collator creation passed\n");
361 coll
->getRules(UCOL_TAILORING_ONLY
, rules
);
362 if (rules
.length() != 0x0a) {
363 errln("English tailored rules failed - length is 0x%x expected 0x%x", rules
.length(), 0x0e);
366 coll
->getRules(UCOL_FULL_RULES
, rules
);
367 if (rules
.length() < 0) {
368 errln("English full rules failed");
374 CollationAPITest::TestDecomposition() {
375 UErrorCode status
= U_ZERO_ERROR
;
376 Collator
*en_US
= Collator::createInstance("en_US", status
),
377 *el_GR
= Collator::createInstance("el_GR", status
),
378 *vi_VN
= Collator::createInstance("vi_VN", status
);
380 if (U_FAILURE(status
)) {
381 errln("ERROR: collation creation failed.\n");
385 /* there is no reason to have canonical decomposition in en_US OR default locale */
386 if (vi_VN
->getAttribute(UCOL_NORMALIZATION_MODE
, status
) != UCOL_ON
)
388 errln("ERROR: vi_VN collation did not have canonical decomposition for normalization!\n");
391 if (el_GR
->getAttribute(UCOL_NORMALIZATION_MODE
, status
) != UCOL_ON
)
393 errln("ERROR: el_GR collation did not have canonical decomposition for normalization!\n");
396 if (en_US
->getAttribute(UCOL_NORMALIZATION_MODE
, status
) != UCOL_OFF
)
398 errln("ERROR: en_US collation had canonical decomposition for normalization!\n");
407 CollationAPITest::TestSafeClone() {
408 static const int CLONETEST_COLLATOR_COUNT
= 3;
409 Collator
*someCollators
[CLONETEST_COLLATOR_COUNT
];
411 UErrorCode err
= U_ZERO_ERROR
;
414 UnicodeString
test1("abCda");
415 UnicodeString
test2("abcda");
417 /* one default collator & two complex ones */
418 someCollators
[0] = Collator::createInstance("en_US", err
);
419 someCollators
[1] = Collator::createInstance("ko", err
);
420 someCollators
[2] = Collator::createInstance("ja_JP", err
);
422 errln("Couldn't instantiate collators. Error: %s", u_errorName(err
));
423 delete someCollators
[0];
424 delete someCollators
[1];
425 delete someCollators
[2];
429 /* change orig & clone & make sure they are independent */
431 for (index
= 0; index
< CLONETEST_COLLATOR_COUNT
; index
++)
433 col
= someCollators
[index
]->safeClone();
435 errln("SafeClone of collator should not return null\n");
438 col
->setStrength(Collator::TERTIARY
);
439 someCollators
[index
]->setStrength(Collator::PRIMARY
);
440 col
->setAttribute(UCOL_CASE_LEVEL
, UCOL_OFF
, err
);
441 someCollators
[index
]->setAttribute(UCOL_CASE_LEVEL
, UCOL_OFF
, err
);
443 doAssert(col
->greater(test1
, test2
), "Result should be \"abCda\" >>> \"abcda\" ");
444 doAssert(someCollators
[index
]->equals(test1
, test2
), "Result should be \"abcda\" == \"abCda\"");
446 delete someCollators
[index
];
451 CollationAPITest::TestHashCode(/* char* par */)
453 logln("hashCode tests begin.");
454 UErrorCode success
= U_ZERO_ERROR
;
456 col1
= Collator::createInstance(Locale::getEnglish(), success
);
457 if (U_FAILURE(success
))
459 errln("Default collation creation failed.");
464 Locale
dk("da", "DK", "");
465 col2
= Collator::createInstance(dk
, success
);
466 if (U_FAILURE(success
))
468 errln("Danish collation creation failed.");
473 col3
= Collator::createInstance(Locale::getEnglish(), success
);
474 if (U_FAILURE(success
))
476 errln("2nd default collation creation failed.");
480 logln("Collator::hashCode() testing ...");
482 doAssert(col1
->hashCode() != col2
->hashCode(), "Hash test1 result incorrect" );
483 doAssert(!(col1
->hashCode() == col2
->hashCode()), "Hash test2 result incorrect" );
484 doAssert(col1
->hashCode() == col3
->hashCode(), "Hash result not equal" );
486 logln("hashCode tests end.");
490 UnicodeString
test1("Abcda");
491 UnicodeString
test2("abcda");
493 CollationKey sortk1
, sortk2
, sortk3
;
494 UErrorCode status
= U_ZERO_ERROR
;
496 col3
->getCollationKey(test1
, sortk1
, status
);
497 col3
->getCollationKey(test2
, sortk2
, status
);
498 col3
->getCollationKey(test2
, sortk3
, status
);
500 doAssert(sortk1
.hashCode() != sortk2
.hashCode(), "Hash test1 result incorrect");
501 doAssert(sortk2
.hashCode() == sortk3
.hashCode(), "Hash result not equal" );
506 //----------------------------------------------------------------------------
507 // CollationKey -- Tests the CollationKey methods
510 CollationAPITest::TestCollationKey(/* char* par */)
512 logln("testing CollationKey begins...");
514 UErrorCode success
=U_ZERO_ERROR
;
515 col
= Collator::createInstance(Locale::getEnglish(), success
);
516 if (U_FAILURE(success
))
518 errln("Default collation creation failed.");
521 col
->setStrength(Collator::TERTIARY
);
523 CollationKey sortk1
, sortk2
;
524 UnicodeString
test1("Abcda"), test2("abcda");
525 UErrorCode key1Status
= U_ZERO_ERROR
, key2Status
= U_ZERO_ERROR
;
527 logln("Testing weird arguments");
528 col
->getCollationKey(NULL
, 0, sortk1
, key1Status
);
529 // key gets reset here
531 sortk1
.getByteArray(length
);
532 doAssert(sortk1
.isBogus() == FALSE
&& length
== 0,
533 "Empty string should return an empty collation key");
534 // bogus key returned here
535 key1Status
= U_ILLEGAL_ARGUMENT_ERROR
;
536 col
->getCollationKey(NULL
, 0, sortk1
, key1Status
);
537 doAssert(sortk1
.getByteArray(length
) == NULL
&& length
== 0,
538 "Error code should return bogus collation key");
540 key1Status
= U_ZERO_ERROR
;
541 logln("Use tertiary comparison level testing ....");
543 col
->getCollationKey(test1
, sortk1
, key1Status
);
544 doAssert((sortk1
.compareTo(col
->getCollationKey(test2
, sortk2
, key2Status
)))
545 == Collator::GREATER
,
546 "Result should be \"Abcda\" >>> \"abcda\"");
548 CollationKey
sortk3(sortk2
), sortkNew
, sortkEmpty
;
552 doAssert((sortk1
!= sortk2
), "The sort keys should be different");
553 doAssert((sortk1
.hashCode() != sortk2
.hashCode()), "sort key hashCode() failed");
554 doAssert((sortk2
== sortk3
), "The sort keys should be the same");
555 doAssert((sortk1
== sortkNew
), "The sort keys assignment failed");
556 doAssert((sortk1
.hashCode() == sortkNew
.hashCode()), "sort key hashCode() failed");
557 doAssert((sortkNew
!= sortk3
), "The sort keys should be different");
558 doAssert(sortk1
.compareTo(sortk3
) == Collator::GREATER
, "Result should be \"Abcda\" >>> \"abcda\"");
559 doAssert(sortk2
.compareTo(sortk3
) == Collator::EQUAL
, "Result should be \"abcda\" == \"abcda\"");
560 doAssert(sortkEmpty
.compareTo(sortk1
) == Collator::LESS
, "Result should be (empty key) <<< \"Abcda\"");
561 doAssert(sortk1
.compareTo(sortkEmpty
) == Collator::GREATER
, "Result should be \"Abcda\" >>> (empty key)");
562 doAssert(sortkEmpty
.compareTo(sortkEmpty
) == Collator::EQUAL
, "Result should be (empty key) == (empty key)");
563 doAssert(sortk1
.compareTo(sortk3
, success
) == UCOL_GREATER
, "Result should be \"Abcda\" >>> \"abcda\"");
564 doAssert(sortk2
.compareTo(sortk3
, success
) == UCOL_EQUAL
, "Result should be \"abcda\" == \"abcda\"");
565 doAssert(sortkEmpty
.compareTo(sortk1
, success
) == UCOL_LESS
, "Result should be (empty key) <<< \"Abcda\"");
566 doAssert(sortk1
.compareTo(sortkEmpty
, success
) == UCOL_GREATER
, "Result should be \"Abcda\" >>> (empty key)");
567 doAssert(sortkEmpty
.compareTo(sortkEmpty
, success
) == UCOL_EQUAL
, "Result should be (empty key) == (empty key)");
569 int32_t cnt1
, cnt2
, cnt3
, cnt4
;
571 const uint8_t* byteArray1
= sortk1
.getByteArray(cnt1
);
572 const uint8_t* byteArray2
= sortk2
.getByteArray(cnt2
);
575 this is a bad test since it is dependent on the version of uca data,
578 const char sortk2_compat[] = {
579 // this is a 1.8 sortkey
580 0x17, 0x19, 0x1B, 0x1D, 0x17, 0x01, 0x08, 0x01, 0x08, 0x00
584 const uint8_t* byteArray3
= 0;
585 byteArray3
= sortk1
.getByteArray(cnt3
);
587 const uint8_t* byteArray4
= 0;
588 byteArray4
= sortk2
.getByteArray(cnt4
);
590 CollationKey
sortk4(byteArray1
, cnt1
), sortk5(byteArray2
, cnt2
);
591 CollationKey
sortk6(byteArray3
, cnt3
), sortk7(byteArray4
, cnt4
);
594 doAssert(memcmp(byteArray2, sortk2_compat, strlen(sortk2_compat)) == 0,
595 "Binary format for 'abcda' sortkey different!");
597 doAssert(sortk1
.compareTo(sortk4
) == Collator::EQUAL
, "CollationKey::toByteArray(sortk1) Failed.");
598 doAssert(sortk2
.compareTo(sortk5
) == Collator::EQUAL
, "CollationKey::toByteArray(sortk2) Failed.");
599 doAssert(sortk4
.compareTo(sortk5
) == Collator::GREATER
, "sortk4 >>> sortk5 Failed");
600 doAssert(sortk1
.compareTo(sortk6
) == Collator::EQUAL
, "CollationKey::getByteArray(sortk1) Failed.");
601 doAssert(sortk2
.compareTo(sortk7
) == Collator::EQUAL
, "CollationKey::getByteArray(sortk2) Failed.");
602 doAssert(sortk6
.compareTo(sortk7
) == Collator::GREATER
, "sortk6 >>> sortk7 Failed");
604 logln("Equality tests : ");
605 doAssert(sortk1
== sortk4
, "sortk1 == sortk4 Failed.");
606 doAssert(sortk2
== sortk5
, "sortk2 == sortk5 Failed.");
607 doAssert(sortk1
!= sortk5
, "sortk1 != sortk5 Failed.");
608 doAssert(sortk1
== sortk6
, "sortk1 == sortk6 Failed.");
609 doAssert(sortk2
== sortk7
, "sortk2 == sortk7 Failed.");
610 doAssert(sortk1
!= sortk7
, "sortk1 != sortk7 Failed.");
616 doAssert(sortk1
== sortk3
, "sortk1 = sortk3 assignment Failed.");
617 doAssert(sortk2
!= sortk3
, "sortk2 != sortk3 Failed.");
618 logln("testing sortkey ends...");
620 col
->setStrength(Collator::SECONDARY
);
621 doAssert(col
->getCollationKey(test1
, sortk1
, key1Status
).compareTo(
622 col
->getCollationKey(test2
, sortk2
, key2Status
))
624 "Result should be \"Abcda\" == \"abcda\"");
628 //----------------------------------------------------------------------------
629 // Tests the CollatorElementIterator class.
630 // ctor, RuleBasedCollator::createCollationElementIterator(), operator==, operator!=
633 CollationAPITest::TestElemIter(/* char* par */)
635 logln("testing sortkey begins...");
637 UErrorCode success
= U_ZERO_ERROR
;
638 col
= Collator::createInstance(Locale::getEnglish(), success
);
639 if (U_FAILURE(success
))
641 errln("Default collation creation failed.");
645 UnicodeString
testString1("XFILE What subset of all possible test cases has the highest probability of detecting the most errors?");
646 UnicodeString
testString2("Xf_ile What subset of all possible test cases has the lowest probability of detecting the least errors?");
647 logln("Constructors and comparison testing....");
648 CollationElementIterator
*iterator1
= ((RuleBasedCollator
*)col
)->createCollationElementIterator(testString1
);
650 CharacterIterator
*chariter
=new StringCharacterIterator(testString1
);
651 CollationElementIterator
*coliter
=((RuleBasedCollator
*)col
)->createCollationElementIterator(*chariter
);
654 CollationElementIterator
*iterator2
= ((RuleBasedCollator
*)col
)->createCollationElementIterator(testString1
);
655 CollationElementIterator
*iterator3
= ((RuleBasedCollator
*)col
)->createCollationElementIterator(testString2
);
657 int32_t offset
= iterator1
->getOffset();
659 errln("Error in getOffset for collation element iterator\n");
662 iterator1
->setOffset(6, success
);
663 if (U_FAILURE(success
)) {
664 errln("Error in setOffset for collation element iterator\n");
667 iterator1
->setOffset(0, success
);
668 int32_t order1
, order2
, order3
;
669 doAssert((*iterator1
== *iterator2
), "The two iterators should be the same");
670 doAssert((*iterator1
!= *iterator3
), "The two iterators should be different");
672 doAssert((*coliter
== *iterator1
), "The two iterators should be the same");
673 doAssert((*coliter
== *iterator2
), "The two iterators should be the same");
674 doAssert((*coliter
!= *iterator3
), "The two iterators should be different");
676 order1
= iterator1
->next(success
);
677 if (U_FAILURE(success
))
679 errln("Somehow ran out of memory stepping through the iterator.");
683 doAssert((*iterator1
!= *iterator2
), "The first iterator advance failed");
684 order2
= iterator2
->getOffset();
685 doAssert((order1
!= order2
), "The order result should not be the same");
686 order2
= iterator2
->next(success
);
687 if (U_FAILURE(success
))
689 errln("Somehow ran out of memory stepping through the iterator.");
693 doAssert((*iterator1
== *iterator2
), "The second iterator advance failed");
694 doAssert((order1
== order2
), "The order result should be the same");
695 order3
= iterator3
->next(success
);
696 if (U_FAILURE(success
))
698 errln("Somehow ran out of memory stepping through the iterator.");
702 doAssert((CollationElementIterator::primaryOrder(order1
) ==
703 CollationElementIterator::primaryOrder(order3
)), "The primary orders should be the same");
704 doAssert((CollationElementIterator::secondaryOrder(order1
) ==
705 CollationElementIterator::secondaryOrder(order3
)), "The secondary orders should be the same");
706 doAssert((CollationElementIterator::tertiaryOrder(order1
) ==
707 CollationElementIterator::tertiaryOrder(order3
)), "The tertiary orders should be the same");
709 order1
= iterator1
->next(success
); order3
= iterator3
->next(success
);
710 if (U_FAILURE(success
))
712 errln("Somehow ran out of memory stepping through the iterator.");
716 doAssert((CollationElementIterator::primaryOrder(order1
) ==
717 CollationElementIterator::primaryOrder(order3
)), "The primary orders should be identical");
718 doAssert((CollationElementIterator::tertiaryOrder(order1
) !=
719 CollationElementIterator::tertiaryOrder(order3
)), "The tertiary orders should be different");
721 order1
= iterator1
->next(success
);
722 order3
= iterator3
->next(success
);
723 /* NO! Secondary orders of two CEs are not related, especially in the case of '_' vs 'I' */
725 doAssert((CollationElementIterator::secondaryOrder(order1) !=
726 CollationElementIterator::secondaryOrder(order3)), "The secondary orders should not be the same");
728 doAssert((order1
!= CollationElementIterator::NULLORDER
), "Unexpected end of iterator reached");
730 iterator1
->reset(); iterator2
->reset(); iterator3
->reset();
731 order1
= iterator1
->next(success
);
732 if (U_FAILURE(success
))
734 errln("Somehow ran out of memory stepping through the iterator.");
738 doAssert((*iterator1
!= *iterator2
), "The first iterator advance failed");
740 order2
= iterator2
->next(success
);
741 if (U_FAILURE(success
))
743 errln("Somehow ran out of memory stepping through the iterator.");
747 doAssert((*iterator1
== *iterator2
), "The second iterator advance failed");
748 doAssert((order1
== order2
), "The order result should be the same");
750 order3
= iterator3
->next(success
);
751 if (U_FAILURE(success
))
753 errln("Somehow ran out of memory stepping through the iterator.");
757 doAssert((CollationElementIterator::primaryOrder(order1
) ==
758 CollationElementIterator::primaryOrder(order3
)), "The primary orders should be the same");
759 doAssert((CollationElementIterator::secondaryOrder(order1
) ==
760 CollationElementIterator::secondaryOrder(order3
)), "The secondary orders should be the same");
761 doAssert((CollationElementIterator::tertiaryOrder(order1
) ==
762 CollationElementIterator::tertiaryOrder(order3
)), "The tertiary orders should be the same");
764 order1
= iterator1
->next(success
); order2
= iterator2
->next(success
); order3
= iterator3
->next(success
);
765 if (U_FAILURE(success
))
767 errln("Somehow ran out of memory stepping through the iterator.");
771 doAssert((CollationElementIterator::primaryOrder(order1
) ==
772 CollationElementIterator::primaryOrder(order3
)), "The primary orders should be identical");
773 doAssert((CollationElementIterator::tertiaryOrder(order1
) !=
774 CollationElementIterator::tertiaryOrder(order3
)), "The tertiary orders should be different");
776 order1
= iterator1
->next(success
); order3
= iterator3
->next(success
);
777 if (U_FAILURE(success
))
779 errln("Somehow ran out of memory stepping through the iterator.");
783 /* NO! Secondary orders of two CEs are not related, especially in the case of '_' vs 'I' */
785 doAssert((CollationElementIterator::secondaryOrder(order1) !=
786 CollationElementIterator::secondaryOrder(order3)), "The secondary orders should not be the same");
788 doAssert((order1
!= CollationElementIterator::NULLORDER
), "Unexpected end of iterator reached");
789 doAssert((*iterator2
!= *iterator3
), "The iterators should be different");
793 success
=U_UNSUPPORTED_ERROR
;
794 Collator
*colerror
=NULL
;
795 colerror
=Collator::createInstance(Locale::getEnglish(), success
);
796 if (colerror
!= 0 || success
== U_ZERO_ERROR
){
797 errln("Error: createInstance(UErrorCode != U_ZERO_ERROR) should just return and not create an instance\n");
799 int32_t position
=coliter
->previous(success
);
800 if(position
!= CollationElementIterator::NULLORDER
){
801 errln((UnicodeString
)"Expected NULLORDER got" + position
);
804 coliter
->setText(*chariter
, success
);
805 if(!U_FAILURE(success
)){
806 errln("Expeceted error");
808 iterator1
->setText((UnicodeString
)"hello there", success
);
809 if(!U_FAILURE(success
)){
810 errln("Expeceted error");
822 logln("testing CollationElementIterator ends...");
825 // Test RuleBasedCollator ctor, dtor, operator==, operator!=, clone, copy, and getRules
827 CollationAPITest::TestOperators(/* char* par */)
829 UErrorCode success
= U_ZERO_ERROR
;
830 UnicodeString
ruleset1("< a, A < b, B < c, C; ch, cH, Ch, CH < d, D, e, E");
831 UnicodeString
ruleset2("< a, A < b, B < c, C < d, D, e, E");
832 RuleBasedCollator
*col1
= new RuleBasedCollator(ruleset1
, success
);
833 if (U_FAILURE(success
)) {
834 errln("RuleBasedCollator creation failed.");
837 success
= U_ZERO_ERROR
;
838 RuleBasedCollator
*col2
= new RuleBasedCollator(ruleset2
, success
);
839 if (U_FAILURE(success
)) {
840 errln("The RuleBasedCollator constructor failed when building with the 2nd rule set.");
843 logln("The operator tests begin : ");
844 logln("testing operator==, operator!=, clone methods ...");
845 doAssert((*col1
!= *col2
), "The two different table collations compared equal");
847 doAssert((*col1
== *col2
), "Collator objects not equal after assignment (operator=)");
849 success
= U_ZERO_ERROR
;
850 Collator
*col3
= Collator::createInstance(Locale::getEnglish(), success
);
851 if (U_FAILURE(success
)) {
852 errln("Default collation creation failed.");
855 doAssert((*col1
!= *col3
), "The two different table collations compared equal");
856 Collator
* col4
= col1
->clone();
857 Collator
* col5
= col3
->clone();
858 doAssert((*col1
== *col4
), "Cloned collation objects not equal");
859 doAssert((*col3
!= *col4
), "Two different table collations compared equal");
860 doAssert((*col3
== *col5
), "Cloned collation objects not equal");
861 doAssert((*col4
!= *col5
), "Two cloned collations compared equal");
863 const UnicodeString
& defRules
= ((RuleBasedCollator
*)col3
)->getRules();
864 RuleBasedCollator
* col6
= new RuleBasedCollator(defRules
, success
);
865 if (U_FAILURE(success
)) {
866 errln("Creating default collation with rules failed.");
869 doAssert((((RuleBasedCollator
*)col3
)->getRules() == col6
->getRules()), "Default collator getRules failed");
871 success
= U_ZERO_ERROR
;
872 RuleBasedCollator
*col7
= new RuleBasedCollator(ruleset2
, Collator::TERTIARY
, success
);
873 if (U_FAILURE(success
)) {
874 errln("The RuleBasedCollator constructor failed when building with the 2nd rule set with tertiary strength.");
877 success
= U_ZERO_ERROR
;
878 RuleBasedCollator
*col8
= new RuleBasedCollator(ruleset2
, UCOL_OFF
, success
);
879 if (U_FAILURE(success
)) {
880 errln("The RuleBasedCollator constructor failed when building with the 2nd rule set with Normalizer::NO_OP.");
883 success
= U_ZERO_ERROR
;
884 RuleBasedCollator
*col9
= new RuleBasedCollator(ruleset2
, Collator::PRIMARY
, UCOL_ON
, success
);
885 if (U_FAILURE(success
)) {
886 errln("The RuleBasedCollator constructor failed when building with the 2nd rule set with tertiary strength and Normalizer::NO_OP.");
889 // doAssert((*col7 == *col8), "The two equal table collations compared different");
890 doAssert((*col7
!= *col9
), "The two different table collations compared equal");
891 doAssert((*col8
!= *col9
), "The two different table collations compared equal");
893 logln("operator tests ended.");
905 // test clone and copy
907 CollationAPITest::TestDuplicate(/* char* par */)
909 UErrorCode status
= U_ZERO_ERROR
;
910 Collator
*col1
= Collator::createInstance(Locale::getEnglish(), status
);
911 if (U_FAILURE(status
)) {
912 logln("Default collator creation failed.");
915 Collator
*col2
= col1
->clone();
916 doAssert((*col1
== *col2
), "Cloned object is not equal to the orginal");
917 UnicodeString
*ruleset
= new UnicodeString("< a, A < b, B < c, C < d, D, e, E");
918 RuleBasedCollator
*col3
= new RuleBasedCollator(*ruleset
, status
);
919 doAssert((*col1
!= *col3
), "Cloned object is equal to some dummy");
920 *col3
= *((RuleBasedCollator
*)col1
);
921 doAssert((*col1
== *col3
), "Copied object is not equal to the orginal");
923 if (U_FAILURE(status
)) {
924 logln("Collation tailoring failed.");
928 UCollationResult res
;
929 UnicodeString
first((UChar
)0x0061);
930 UnicodeString
second((UChar
)0x0062);
931 UnicodeString
copiedEnglishRules(((RuleBasedCollator
*)col1
)->getRules());
936 // Try using the cloned collators after deleting the original data
937 res
= col2
->compare(first
, second
, status
);
938 if(res
!= UCOL_LESS
) {
939 errln("a should be less then b after tailoring");
941 if (((RuleBasedCollator
*)col2
)->getRules() != copiedEnglishRules
) {
942 errln(UnicodeString("English rule difference. ")
943 + copiedEnglishRules
+ UnicodeString("\ngetRules=") + ((RuleBasedCollator
*)col2
)->getRules());
945 res
= col3
->compare(first
, second
, status
);
946 if(res
!= UCOL_LESS
) {
947 errln("a should be less then b after tailoring");
949 if (col3
->getRules() != copiedEnglishRules
) {
950 errln(UnicodeString("English rule difference. ")
951 + copiedEnglishRules
+ UnicodeString("\ngetRules=") + col3
->getRules());
959 CollationAPITest::TestCompare(/* char* par */)
961 logln("The compare tests begin : ");
963 UErrorCode success
= U_ZERO_ERROR
;
964 col
= Collator::createInstance(Locale::getEnglish(), success
);
965 if (U_FAILURE(success
)) {
966 errln("Default collation creation failed.");
969 UnicodeString
test1("Abcda"), test2("abcda");
970 logln("Use tertiary comparison level testing ....");
972 doAssert((!col
->equals(test1
, test2
) ), "Result should be \"Abcda\" != \"abcda\"");
973 doAssert((col
->greater(test1
, test2
) ), "Result should be \"Abcda\" >>> \"abcda\"");
974 doAssert((col
->greaterOrEqual(test1
, test2
) ), "Result should be \"Abcda\" >>> \"abcda\"");
976 col
->setStrength(Collator::SECONDARY
);
977 logln("Use secondary comparison level testing ....");
979 doAssert((col
->equals(test1
, test2
) ), "Result should be \"Abcda\" == \"abcda\"");
980 doAssert((!col
->greater(test1
, test2
) ), "Result should be \"Abcda\" == \"abcda\"");
981 doAssert((col
->greaterOrEqual(test1
, test2
) ), "Result should be \"Abcda\" == \"abcda\"");
983 col
->setStrength(Collator::PRIMARY
);
984 logln("Use primary comparison level testing ....");
986 doAssert((col
->equals(test1
, test2
) ), "Result should be \"Abcda\" == \"abcda\"");
987 doAssert((!col
->greater(test1
, test2
) ), "Result should be \"Abcda\" == \"abcda\"");
988 doAssert((col
->greaterOrEqual(test1
, test2
) ), "Result should be \"Abcda\" == \"abcda\"");
990 // Test different APIs
991 const UChar
* t1
= test1
.getBuffer();
992 int32_t t1Len
= test1
.length();
993 const UChar
* t2
= test2
.getBuffer();
994 int32_t t2Len
= test2
.length();
996 doAssert((col
->compare(test1
, test2
) == Collator::EQUAL
), "Problem");
997 doAssert((col
->compare(test1
, test2
, success
) == UCOL_EQUAL
), "Problem");
998 doAssert((col
->compare(t1
, t1Len
, t2
, t2Len
) == Collator::EQUAL
), "Problem");
999 doAssert((col
->compare(t1
, t1Len
, t2
, t2Len
, success
) == UCOL_EQUAL
), "Problem");
1000 doAssert((col
->compare(test1
, test2
, t1Len
) == Collator::EQUAL
), "Problem");
1001 doAssert((col
->compare(test1
, test2
, t1Len
, success
) == UCOL_EQUAL
), "Problem");
1003 col
->setAttribute(UCOL_STRENGTH
, UCOL_TERTIARY
, success
);
1004 doAssert((col
->compare(test1
, test2
) == Collator::GREATER
), "Problem");
1005 doAssert((col
->compare(test1
, test2
, success
) == UCOL_GREATER
), "Problem");
1006 doAssert((col
->compare(t1
, t1Len
, t2
, t2Len
) == Collator::GREATER
), "Problem");
1007 doAssert((col
->compare(t1
, t1Len
, t2
, t2Len
, success
) == UCOL_GREATER
), "Problem");
1008 doAssert((col
->compare(test1
, test2
, t1Len
) == Collator::GREATER
), "Problem");
1009 doAssert((col
->compare(test1
, test2
, t1Len
, success
) == UCOL_GREATER
), "Problem");
1013 logln("The compare tests end.");
1018 CollationAPITest::TestGetAll(/* char* par */)
1021 const Locale
* list
= Collator::getAvailableLocales(count
);
1022 for (int32_t i
= 0; i
< count
; ++i
) {
1023 UnicodeString locName
, dispName
;
1024 log("Locale name: ");
1025 log(list
[i
].getName());
1026 log(" , the display name is : ");
1027 logln(list
[i
].getDisplayName(dispName
));
1031 void CollationAPITest::TestSortKey()
1033 UErrorCode status
= U_ZERO_ERROR
;
1035 this is supposed to open default date format, but later on it treats
1036 it like it is "en_US"
1037 - very bad if you try to run the tests on machine where default
1038 locale is NOT "en_US"
1040 Collator
*col
= Collator::createInstance(Locale::getEnglish(), status
);
1041 if (U_FAILURE(status
)) {
1042 errln("ERROR: Default collation creation failed.: %s\n", u_errorName(status
));
1046 if (col
->getStrength() != Collator::TERTIARY
)
1048 errln("ERROR: default collation did not have UCOL_DEFAULT_STRENGTH !\n");
1051 /* Need to use identical strength */
1052 col
->setAttribute(UCOL_STRENGTH
, UCOL_IDENTICAL
, status
);
1054 uint8_t key2compat
[] = {
1055 /* 3.6 key, from UCA 5.0 */
1056 0x29, 0x2b, 0x2d, 0x2f, 0x29, 0x01,
1057 0x09, 0x01, 0x09, 0x01, 0x28, 0x01,
1058 0x92, 0x93, 0x94, 0x95, 0x92, 0x00
1060 /* 3.4 key, from UCA 4.1 */
1062 0x28, 0x2a, 0x2c, 0x2e, 0x28, 0x01,
1063 0x09, 0x01, 0x09, 0x01, 0x27, 0x01,
1064 0x92, 0x93, 0x94, 0x95, 0x92, 0x00
1068 0x26, 0x28, 0x2A, 0x2C, 0x26, 0x01,
1069 0x09, 0x01, 0x09, 0x01, 0x25, 0x01,
1070 0x92, 0x93, 0x94, 0x95, 0x92, 0x00
1074 0x1D, 0x1F, 0x21, 0x23, 0x1D, 0x01,
1075 0x09, 0x01, 0x09, 0x01, 0x1C, 0x01,
1076 0x92, 0x93, 0x94, 0x95, 0x92, 0x00
1080 0x19, 0x1B, 0x1D, 0x1F, 0x19,
1081 0x01, 0x09, 0x01, 0x09, 0x01,
1083 0x92, 0x93, 0x94, 0x95, 0x92,
1088 0x19, 0x1B, 0x1D, 0x1F, 0x19,
1089 0x01, 0x0A, 0x01, 0x0A, 0x01,
1090 0x92, 0x93, 0x94, 0x95, 0x92,
1095 UChar test1
[6] = {0x41, 0x62, 0x63, 0x64, 0x61, 0},
1096 test2
[6] = {0x61, 0x62, 0x63, 0x64, 0x61, 0},
1097 test3
[6] = {0x61, 0x62, 0x63, 0x64, 0x61, 0};
1099 uint8_t sortkey1
[64];
1100 uint8_t sortkey2
[64];
1101 uint8_t sortkey3
[64];
1103 logln("Use tertiary comparison level testing ....\n");
1106 col
->getCollationKey(test1
, u_strlen(test1
), key1
, status
);
1109 col
->getCollationKey(test2
, u_strlen(test2
), key2
, status
);
1112 col
->getCollationKey(test3
, u_strlen(test3
), key3
, status
);
1114 doAssert(key1
.compareTo(key2
) == Collator::GREATER
,
1115 "Result should be \"Abcda\" > \"abcda\"");
1116 doAssert(key2
.compareTo(key1
) == Collator::LESS
,
1117 "Result should be \"abcda\" < \"Abcda\"");
1118 doAssert(key2
.compareTo(key3
) == Collator::EQUAL
,
1119 "Result should be \"abcda\" == \"abcda\"");
1121 int32_t keylength
= 0;
1122 doAssert(strcmp((const char *)(key2
.getByteArray(keylength
)),
1123 (const char *)key2compat
) == 0,
1124 "Binary format for 'abcda' sortkey different!");
1126 col
->getSortKey(test1
, sortkey1
, 64);
1127 col
->getSortKey(test2
, sortkey2
, 64);
1128 col
->getSortKey(test3
, sortkey3
, 64);
1130 const uint8_t *tempkey
= key1
.getByteArray(keylength
);
1131 doAssert(memcmp(tempkey
, sortkey1
, keylength
) == 0,
1132 "Test1 string should have the same collation key and sort key");
1133 tempkey
= key2
.getByteArray(keylength
);
1134 doAssert(memcmp(tempkey
, sortkey2
, keylength
) == 0,
1135 "Test2 string should have the same collation key and sort key");
1136 tempkey
= key3
.getByteArray(keylength
);
1137 doAssert(memcmp(tempkey
, sortkey3
, keylength
) == 0,
1138 "Test3 string should have the same collation key and sort key");
1140 col
->getSortKey(test1
, 5, sortkey1
, 64);
1141 col
->getSortKey(test2
, 5, sortkey2
, 64);
1142 col
->getSortKey(test3
, 5, sortkey3
, 64);
1144 tempkey
= key1
.getByteArray(keylength
);
1145 doAssert(memcmp(tempkey
, sortkey1
, keylength
) == 0,
1146 "Test1 string should have the same collation key and sort key");
1147 tempkey
= key2
.getByteArray(keylength
);
1148 doAssert(memcmp(tempkey
, sortkey2
, keylength
) == 0,
1149 "Test2 string should have the same collation key and sort key");
1150 tempkey
= key3
.getByteArray(keylength
);
1151 doAssert(memcmp(tempkey
, sortkey3
, keylength
) == 0,
1152 "Test3 string should have the same collation key and sort key");
1154 UnicodeString
strtest1(test1
);
1155 col
->getSortKey(strtest1
, sortkey1
, 64);
1156 UnicodeString
strtest2(test2
);
1157 col
->getSortKey(strtest2
, sortkey2
, 64);
1158 UnicodeString
strtest3(test3
);
1159 col
->getSortKey(strtest3
, sortkey3
, 64);
1161 tempkey
= key1
.getByteArray(keylength
);
1162 doAssert(memcmp(tempkey
, sortkey1
, keylength
) == 0,
1163 "Test1 string should have the same collation key and sort key");
1164 tempkey
= key2
.getByteArray(keylength
);
1165 doAssert(memcmp(tempkey
, sortkey2
, keylength
) == 0,
1166 "Test2 string should have the same collation key and sort key");
1167 tempkey
= key3
.getByteArray(keylength
);
1168 doAssert(memcmp(tempkey
, sortkey3
, keylength
) == 0,
1169 "Test3 string should have the same collation key and sort key");
1171 logln("Use secondary comparision level testing ...\n");
1172 col
->setStrength(Collator::SECONDARY
);
1174 col
->getCollationKey(test1
, u_strlen(test1
), key1
, status
);
1175 col
->getCollationKey(test2
, u_strlen(test2
), key2
, status
);
1176 col
->getCollationKey(test3
, u_strlen(test3
), key3
, status
);
1178 doAssert(key1
.compareTo(key2
) == Collator::EQUAL
,
1179 "Result should be \"Abcda\" == \"abcda\"");
1180 doAssert(key2
.compareTo(key3
) == Collator::EQUAL
,
1181 "Result should be \"abcda\" == \"abcda\"");
1183 tempkey
= key2
.getByteArray(keylength
);
1184 doAssert(memcmp(tempkey
, key2compat
, keylength
- 1) == 0,
1185 "Binary format for 'abcda' sortkey different!");
1187 col
->getSortKey(test1
, sortkey1
, 64);
1188 col
->getSortKey(test2
, sortkey2
, 64);
1189 col
->getSortKey(test3
, sortkey3
, 64);
1191 tempkey
= key1
.getByteArray(keylength
);
1192 doAssert(memcmp(tempkey
, sortkey1
, keylength
) == 0,
1193 "Test1 string should have the same collation key and sort key");
1194 tempkey
= key2
.getByteArray(keylength
);
1195 doAssert(memcmp(tempkey
, sortkey2
, keylength
) == 0,
1196 "Test2 string should have the same collation key and sort key");
1197 tempkey
= key3
.getByteArray(keylength
);
1198 doAssert(memcmp(tempkey
, sortkey3
, keylength
) == 0,
1199 "Test3 string should have the same collation key and sort key");
1201 col
->getSortKey(test1
, 5, sortkey1
, 64);
1202 col
->getSortKey(test2
, 5, sortkey2
, 64);
1203 col
->getSortKey(test3
, 5, sortkey3
, 64);
1205 tempkey
= key1
.getByteArray(keylength
);
1206 doAssert(memcmp(tempkey
, sortkey1
, keylength
) == 0,
1207 "Test1 string should have the same collation key and sort key");
1208 tempkey
= key2
.getByteArray(keylength
);
1209 doAssert(memcmp(tempkey
, sortkey2
, keylength
) == 0,
1210 "Test2 string should have the same collation key and sort key");
1211 tempkey
= key3
.getByteArray(keylength
);
1212 doAssert(memcmp(tempkey
, sortkey3
, keylength
) == 0,
1213 "Test3 string should have the same collation key and sort key");
1215 col
->getSortKey(strtest1
, sortkey1
, 64);
1216 col
->getSortKey(strtest2
, sortkey2
, 64);
1217 col
->getSortKey(strtest3
, sortkey3
, 64);
1219 tempkey
= key1
.getByteArray(keylength
);
1220 doAssert(memcmp(tempkey
, sortkey1
, keylength
) == 0,
1221 "Test1 string should have the same collation key and sort key");
1222 tempkey
= key2
.getByteArray(keylength
);
1223 doAssert(memcmp(tempkey
, sortkey2
, keylength
) == 0,
1224 "Test2 string should have the same collation key and sort key");
1225 tempkey
= key3
.getByteArray(keylength
);
1226 doAssert(memcmp(tempkey
, sortkey3
, keylength
) == 0,
1227 "Test3 string should have the same collation key and sort key");
1229 logln("testing sortkey ends...");
1233 void CollationAPITest::TestMaxExpansion()
1235 UErrorCode status
= U_ZERO_ERROR
;
1237 UChar32 unassigned
= 0xEFFFD;
1238 uint32_t sorder
= 0;
1239 uint32_t temporder
= 0;
1241 UnicodeString
rule("&a < ab < c/aba < d < z < ch");
1242 RuleBasedCollator
coll(rule
, status
);
1243 if(U_FAILURE(status
)) {
1244 errln("Collator creation failed with error %s", u_errorName(status
));
1247 UnicodeString
str(ch
);
1248 CollationElementIterator
*iter
=
1249 coll
.createCollationElementIterator(str
);
1251 while (ch
< 0xFFFF && U_SUCCESS(status
)) {
1258 str
.setCharAt(0, ch
);
1259 iter
->setText(str
, status
);
1260 order
= iter
->previous(status
);
1262 /* thai management */
1264 order
= iter
->previous(status
);
1266 while (U_SUCCESS(status
) && iter
->previous(status
) != UCOL_NULLORDER
) {
1270 size
= coll
.getMaxExpansion(order
);
1271 if (U_FAILURE(status
) || size
< count
) {
1272 errln("Failure at codepoint %d, maximum expansion count < %d\n",
1277 /* testing for exact max expansion */
1282 str
.setCharAt(0, ch
);
1283 iter
->setText(str
, status
);
1284 order
= iter
->previous(status
);
1285 size
= coll
.getMaxExpansion(order
);
1286 if (U_FAILURE(status
) || size
!= 1) {
1287 errln("Failure at codepoint %d, maximum expansion count < %d\n",
1295 iter
->setText(str
, status
);
1296 temporder
= iter
->previous(status
);
1298 if (U_FAILURE(status
) || coll
.getMaxExpansion(temporder
) != 3) {
1299 errln("Failure at codepoint %d, maximum expansion count != %d\n",
1305 iter
->setText(str
, status
);
1306 temporder
= iter
->previous(status
);
1308 if (U_FAILURE(status
) || coll
.getMaxExpansion(temporder
) != 1) {
1309 errln("Failure at codepoint %d, maximum expansion count != %d\n",
1313 str
.setTo(unassigned
);
1314 iter
->setText(str
, status
);
1315 sorder
= iter
->previous(status
);
1317 if (U_FAILURE(status
) || coll
.getMaxExpansion(sorder
) != 2) {
1318 errln("Failure at supplementary codepoints, maximum expansion count < %d\n",
1325 iter
->setText(str
, status
);
1326 temporder
= iter
->previous(status
);
1327 if (U_FAILURE(status
) || coll
.getMaxExpansion(temporder
) > 3) {
1328 errln("Failure at codepoint %d, maximum expansion count > %d\n",
1334 /* testing special jamo &a<\u1160 */
1335 rule
= CharsToUnicodeString("\\u0026\\u0071\\u003c\\u1165\\u002f\\u0071\\u0071\\u0071\\u0071");
1337 RuleBasedCollator
jamocoll(rule
, status
);
1338 iter
= jamocoll
.createCollationElementIterator(str
);
1339 temporder
= iter
->previous(status
);
1340 if (U_FAILURE(status
) || iter
->getMaxExpansion(temporder
) != 6) {
1341 errln("Failure at codepoint %d, maximum expansion count > %d\n",
1348 void CollationAPITest::TestDisplayName()
1350 UErrorCode error
= U_ZERO_ERROR
;
1351 Collator
*coll
= Collator::createInstance("en_US", error
);
1352 if (U_FAILURE(error
)) {
1353 errln("Failure creating english collator");
1357 UnicodeString result
;
1358 coll
->getDisplayName(Locale::getCanadaFrench(), result
);
1359 Locale::getCanadaFrench().getDisplayName(name
);
1360 if (result
.compare(name
)) {
1361 errln("Failure getting the correct name for locale en_US");
1364 coll
->getDisplayName(Locale::getSimplifiedChinese(), result
);
1365 Locale::getSimplifiedChinese().getDisplayName(name
);
1366 if (result
.compare(name
)) {
1367 errln("Failure getting the correct name for locale zh_SG");
1372 void CollationAPITest::TestAttribute()
1374 UErrorCode error
= U_ZERO_ERROR
;
1375 Collator
*coll
= Collator::createInstance(error
);
1377 if (U_FAILURE(error
)) {
1378 errln("Creation of default collator failed");
1382 coll
->setAttribute(UCOL_FRENCH_COLLATION
, UCOL_OFF
, error
);
1383 if (coll
->getAttribute(UCOL_FRENCH_COLLATION
, error
) != UCOL_OFF
||
1385 errln("Setting and retrieving of the french collation failed");
1388 coll
->setAttribute(UCOL_FRENCH_COLLATION
, UCOL_ON
, error
);
1389 if (coll
->getAttribute(UCOL_FRENCH_COLLATION
, error
) != UCOL_ON
||
1391 errln("Setting and retrieving of the french collation failed");
1394 coll
->setAttribute(UCOL_ALTERNATE_HANDLING
, UCOL_SHIFTED
, error
);
1395 if (coll
->getAttribute(UCOL_ALTERNATE_HANDLING
, error
) != UCOL_SHIFTED
||
1397 errln("Setting and retrieving of the alternate handling failed");
1400 coll
->setAttribute(UCOL_ALTERNATE_HANDLING
, UCOL_NON_IGNORABLE
, error
);
1401 if (coll
->getAttribute(UCOL_ALTERNATE_HANDLING
, error
) != UCOL_NON_IGNORABLE
||
1403 errln("Setting and retrieving of the alternate handling failed");
1406 coll
->setAttribute(UCOL_CASE_FIRST
, UCOL_LOWER_FIRST
, error
);
1407 if (coll
->getAttribute(UCOL_CASE_FIRST
, error
) != UCOL_LOWER_FIRST
||
1409 errln("Setting and retrieving of the case first attribute failed");
1412 coll
->setAttribute(UCOL_CASE_FIRST
, UCOL_UPPER_FIRST
, error
);
1413 if (coll
->getAttribute(UCOL_CASE_FIRST
, error
) != UCOL_UPPER_FIRST
||
1415 errln("Setting and retrieving of the case first attribute failed");
1418 coll
->setAttribute(UCOL_CASE_LEVEL
, UCOL_ON
, error
);
1419 if (coll
->getAttribute(UCOL_CASE_LEVEL
, error
) != UCOL_ON
||
1421 errln("Setting and retrieving of the case level attribute failed");
1424 coll
->setAttribute(UCOL_CASE_LEVEL
, UCOL_OFF
, error
);
1425 if (coll
->getAttribute(UCOL_CASE_LEVEL
, error
) != UCOL_OFF
||
1427 errln("Setting and retrieving of the case level attribute failed");
1430 coll
->setAttribute(UCOL_NORMALIZATION_MODE
, UCOL_ON
, error
);
1431 if (coll
->getAttribute(UCOL_NORMALIZATION_MODE
, error
) != UCOL_ON
||
1433 errln("Setting and retrieving of the normalization on/off attribute failed");
1436 coll
->setAttribute(UCOL_NORMALIZATION_MODE
, UCOL_OFF
, error
);
1437 if (coll
->getAttribute(UCOL_NORMALIZATION_MODE
, error
) != UCOL_OFF
||
1439 errln("Setting and retrieving of the normalization on/off attribute failed");
1442 coll
->setAttribute(UCOL_STRENGTH
, UCOL_PRIMARY
, error
);
1443 if (coll
->getAttribute(UCOL_STRENGTH
, error
) != UCOL_PRIMARY
||
1445 errln("Setting and retrieving of the collation strength failed");
1448 coll
->setAttribute(UCOL_STRENGTH
, UCOL_SECONDARY
, error
);
1449 if (coll
->getAttribute(UCOL_STRENGTH
, error
) != UCOL_SECONDARY
||
1451 errln("Setting and retrieving of the collation strength failed");
1454 coll
->setAttribute(UCOL_STRENGTH
, UCOL_TERTIARY
, error
);
1455 if (coll
->getAttribute(UCOL_STRENGTH
, error
) != UCOL_TERTIARY
||
1457 errln("Setting and retrieving of the collation strength failed");
1460 coll
->setAttribute(UCOL_STRENGTH
, UCOL_QUATERNARY
, error
);
1461 if (coll
->getAttribute(UCOL_STRENGTH
, error
) != UCOL_QUATERNARY
||
1463 errln("Setting and retrieving of the collation strength failed");
1466 coll
->setAttribute(UCOL_STRENGTH
, UCOL_IDENTICAL
, error
);
1467 if (coll
->getAttribute(UCOL_STRENGTH
, error
) != UCOL_IDENTICAL
||
1469 errln("Setting and retrieving of the collation strength failed");
1475 void CollationAPITest::TestVariableTopSetting() {
1476 UErrorCode status
= U_ZERO_ERROR
;
1478 UChar vt
[256] = { 0 };
1480 Collator
*coll
= Collator::createInstance(status
);
1481 if(U_FAILURE(status
)) {
1483 errln("Collator creation failed with error %s", u_errorName(status
));
1487 uint32_t oldVarTop
= coll
->getVariableTop(status
);
1491 uint32_t newVarTop
= coll
->setVariableTop(vt
, 1, status
);
1493 if((newVarTop
& 0xFFFF0000) != (coll
->getVariableTop(status
) & 0xFFFF0000)) {
1494 errln("Didn't set vartop properly\n");
1497 coll
->setVariableTop(oldVarTop
, status
);
1499 uint32_t newerVarTop
= coll
->setVariableTop(UnicodeString(vt
, 1), status
);
1501 if((newVarTop
& 0xFFFF0000) != (newerVarTop
& 0xFFFF0000)) {
1502 errln("Didn't set vartop properly from UnicodeString!\n");
1509 void CollationAPITest::TestGetLocale() {
1510 UErrorCode status
= U_ZERO_ERROR
;
1511 const char *rules
= "&a<x<y<z";
1512 UChar rlz
[256] = {0};
1514 Collator
*coll
= NULL
;
1519 static const struct {
1520 const char* requestedLocale
;
1521 const char* validLocale
;
1522 const char* actualLocale
;
1524 { "sr_YU", "sr_YU", "root" },
1525 { "sh_YU", "sh_YU", "sh" },
1526 { "en_US_CALIFORNIA", "en_US", "root" },
1527 { "fr_FR_NONEXISTANT", "fr_FR", "fr" }
1530 u_unescape(rules
, rlz
, 256);
1532 /* test opening collators for different locales */
1533 for(i
= 0; i
<(int32_t)(sizeof(testStruct
)/sizeof(testStruct
[0])); i
++) {
1534 status
= U_ZERO_ERROR
;
1535 coll
= Collator::createInstance(testStruct
[i
].requestedLocale
, status
);
1536 if(U_FAILURE(status
)) {
1537 log("Failed to open collator for %s with %s\n", testStruct
[i
].requestedLocale
, u_errorName(status
));
1541 locale
= coll
->getLocale(ULOC_REQUESTED_LOCALE
, status
);
1542 if(locale
!= testStruct
[i
].requestedLocale
) {
1543 log("[Coll %s]: Error in requested locale, expected %s, got %s\n", testStruct
[i
].requestedLocale
, testStruct
[i
].requestedLocale
, locale
.getName());
1545 locale
= coll
->getLocale(ULOC_VALID_LOCALE
, status
);
1546 if(locale
!= testStruct
[i
].validLocale
) {
1547 log("[Coll %s]: Error in valid locale, expected %s, got %s\n", testStruct
[i
].requestedLocale
, testStruct
[i
].validLocale
, locale
.getName());
1549 locale
= coll
->getLocale(ULOC_ACTUAL_LOCALE
, status
);
1550 if(locale
!= testStruct
[i
].actualLocale
) {
1551 log("[Coll %s]: Error in actual locale, expected %s, got %s\n", testStruct
[i
].requestedLocale
, testStruct
[i
].actualLocale
, locale
.getName());
1556 /* completely non-existant locale for collator should get a default collator */
1558 Collator
*defaultColl
= Collator::createInstance((const Locale
)NULL
, status
);
1559 coll
= Collator::createInstance("blahaha", status
);
1560 if(U_FAILURE(status
)) {
1561 log("Failed to open collator with %s\n", u_errorName(status
));
1566 if(coll
->getLocale(ULOC_REQUESTED_LOCALE
, status
) != "blahaha") {
1567 log("Nonexisting locale didn't preserve the requested locale\n");
1569 if(coll
->getLocale(ULOC_VALID_LOCALE
, status
) !=
1570 defaultColl
->getLocale(ULOC_VALID_LOCALE
, status
)) {
1571 log("Valid locale for nonexisting locale locale collator differs "
1572 "from valid locale for default collator\n");
1574 if(coll
->getLocale(ULOC_ACTUAL_LOCALE
, status
) !=
1575 defaultColl
->getLocale(ULOC_ACTUAL_LOCALE
, status
)) {
1576 log("Actual locale for nonexisting locale locale collator differs "
1577 "from actual locale for default collator\n");
1585 /* collator instantiated from rules should have all three locales NULL */
1586 coll
= new RuleBasedCollator(rlz
, status
);
1587 locale
= coll
->getLocale(ULOC_REQUESTED_LOCALE
, status
);
1588 if(!locale
.isBogus()) {
1589 log("For collator instantiated from rules, requested locale %s is not bogus\n", locale
.getName());
1591 locale
= coll
->getLocale(ULOC_VALID_LOCALE
, status
);
1592 if(!locale
.isBogus()) {
1593 log("For collator instantiated from rules, valid locale %s is not bogus\n", locale
.getName());
1595 locale
= coll
->getLocale(ULOC_ACTUAL_LOCALE
, status
);
1596 if(!locale
.isBogus()) {
1597 log("For collator instantiated from rules, actual locale %s is not bogus\n", locale
.getName());
1603 const char *original
;
1610 static int U_CALLCONV
1611 compare_teststruct(const void *string1
, const void *string2
) {
1612 return(strcmp((const char *)((struct teststruct
*)string1
)->key
, (const char *)((struct teststruct
*)string2
)->key
));
1617 void CollationAPITest::TestBounds(void) {
1618 UErrorCode status
= U_ZERO_ERROR
;
1620 Collator
*coll
= Collator::createInstance(Locale("sh"), status
);
1621 if(U_FAILURE(status
)) {
1623 errln("Collator creation failed with %s", u_errorName(status
));
1627 uint8_t sortkey
[512], lower
[512], upper
[512];
1630 const char *test
[] = {
1634 "j\\u00F6hn sm\\u00EFth",
1635 "J\\u00F6hn Sm\\u00EFth",
1636 "J\\u00D6HN SM\\u00CFTH",
1641 static struct teststruct tests
[] = {
1642 {"\\u010CAKI MIHALJ", {0}},
1643 {"\\u010CAKI MIHALJ", {0}},
1644 {"\\u010CAKI PIRO\\u0160KA", {0}},
1645 {"\\u010CABAI ANDRIJA", {0}},
1646 {"\\u010CABAI LAJO\\u0160", {0}},
1647 {"\\u010CABAI MARIJA", {0}},
1648 {"\\u010CABAI STEVAN", {0}},
1649 {"\\u010CABAI STEVAN", {0}},
1650 {"\\u010CABARKAPA BRANKO", {0}},
1651 {"\\u010CABARKAPA MILENKO", {0}},
1652 {"\\u010CABARKAPA MIROSLAV", {0}},
1653 {"\\u010CABARKAPA SIMO", {0}},
1654 {"\\u010CABARKAPA STANKO", {0}},
1655 {"\\u010CABARKAPA TAMARA", {0}},
1656 {"\\u010CABARKAPA TOMA\\u0160", {0}},
1657 {"\\u010CABDARI\\u0106 NIKOLA", {0}},
1658 {"\\u010CABDARI\\u0106 ZORICA", {0}},
1659 {"\\u010CABI NANDOR", {0}},
1660 {"\\u010CABOVI\\u0106 MILAN", {0}},
1661 {"\\u010CABRADI AGNEZIJA", {0}},
1662 {"\\u010CABRADI IVAN", {0}},
1663 {"\\u010CABRADI JELENA", {0}},
1664 {"\\u010CABRADI LJUBICA", {0}},
1665 {"\\u010CABRADI STEVAN", {0}},
1666 {"\\u010CABRDA MARTIN", {0}},
1667 {"\\u010CABRILO BOGDAN", {0}},
1668 {"\\u010CABRILO BRANISLAV", {0}},
1669 {"\\u010CABRILO LAZAR", {0}},
1670 {"\\u010CABRILO LJUBICA", {0}},
1671 {"\\u010CABRILO SPASOJA", {0}},
1672 {"\\u010CADE\\u0160 ZDENKA", {0}},
1673 {"\\u010CADESKI BLAGOJE", {0}},
1674 {"\\u010CADOVSKI VLADIMIR", {0}},
1675 {"\\u010CAGLJEVI\\u0106 TOMA", {0}},
1676 {"\\u010CAGOROVI\\u0106 VLADIMIR", {0}},
1677 {"\\u010CAJA VANKA", {0}},
1678 {"\\u010CAJI\\u0106 BOGOLJUB", {0}},
1679 {"\\u010CAJI\\u0106 BORISLAV", {0}},
1680 {"\\u010CAJI\\u0106 RADOSLAV", {0}},
1681 {"\\u010CAK\\u0160IRAN MILADIN", {0}},
1682 {"\\u010CAKAN EUGEN", {0}},
1683 {"\\u010CAKAN EVGENIJE", {0}},
1684 {"\\u010CAKAN IVAN", {0}},
1685 {"\\u010CAKAN JULIJAN", {0}},
1686 {"\\u010CAKAN MIHAJLO", {0}},
1687 {"\\u010CAKAN STEVAN", {0}},
1688 {"\\u010CAKAN VLADIMIR", {0}},
1689 {"\\u010CAKAN VLADIMIR", {0}},
1690 {"\\u010CAKAN VLADIMIR", {0}},
1691 {"\\u010CAKARA ANA", {0}},
1692 {"\\u010CAKAREVI\\u0106 MOMIR", {0}},
1693 {"\\u010CAKAREVI\\u0106 NEDELJKO", {0}},
1694 {"\\u010CAKI \\u0160ANDOR", {0}},
1695 {"\\u010CAKI AMALIJA", {0}},
1696 {"\\u010CAKI ANDRA\\u0160", {0}},
1697 {"\\u010CAKI LADISLAV", {0}},
1698 {"\\u010CAKI LAJO\\u0160", {0}},
1699 {"\\u010CAKI LASLO", {0}}
1704 int32_t i
= 0, j
= 0, k
= 0, buffSize
= 0, skSize
= 0, lowerSize
= 0, upperSize
= 0;
1705 int32_t arraySize
= sizeof(tests
)/sizeof(tests
[0]);
1707 for(i
= 0; i
<arraySize
; i
++) {
1708 buffSize
= u_unescape(tests
[i
].original
, buffer
, 512);
1709 skSize
= coll
->getSortKey(buffer
, buffSize
, tests
[i
].key
, 512);
1712 qsort(tests
, arraySize
, sizeof(struct teststruct
), compare_teststruct
);
1714 for(i
= 0; i
< arraySize
-1; i
++) {
1715 for(j
= i
+1; j
< arraySize
; j
++) {
1716 lowerSize
= coll
->getBound(tests
[i
].key
, -1, UCOL_BOUND_LOWER
, 1, lower
, 512, status
);
1717 upperSize
= coll
->getBound(tests
[j
].key
, -1, UCOL_BOUND_UPPER
, 1, upper
, 512, status
);
1718 for(k
= i
; k
<= j
; k
++) {
1719 if(strcmp((const char *)lower
, (const char *)tests
[k
].key
) > 0) {
1720 errln("Problem with lower! j = %i (%s vs %s)", k
, tests
[k
].original
, tests
[i
].original
);
1722 if(strcmp((const char *)upper
, (const char *)tests
[k
].key
) <= 0) {
1723 errln("Problem with upper! j = %i (%s vs %s)", k
, tests
[k
].original
, tests
[j
].original
);
1730 for(i
= 0; i
<(int32_t)(sizeof(test
)/sizeof(test
[0])); i
++) {
1731 buffSize
= u_unescape(test
[i
], buffer
, 512);
1732 skSize
= coll
->getSortKey(buffer
, buffSize
, sortkey
, 512);
1733 lowerSize
= ucol_getBound(sortkey
, skSize
, UCOL_BOUND_LOWER
, 1, lower
, 512, &status
);
1734 upperSize
= ucol_getBound(sortkey
, skSize
, UCOL_BOUND_UPPER_LONG
, 1, upper
, 512, &status
);
1735 for(j
= i
+1; j
<(int32_t)(sizeof(test
)/sizeof(test
[0])); j
++) {
1736 buffSize
= u_unescape(test
[j
], buffer
, 512);
1737 skSize
= coll
->getSortKey(buffer
, buffSize
, sortkey
, 512);
1738 if(strcmp((const char *)lower
, (const char *)sortkey
) > 0) {
1739 errln("Problem with lower! i = %i, j = %i (%s vs %s)", i
, j
, test
[i
], test
[j
]);
1741 if(strcmp((const char *)upper
, (const char *)sortkey
) <= 0) {
1742 errln("Problem with upper! i = %i, j = %i (%s vs %s)", i
, j
, test
[i
], test
[j
]);
1750 void CollationAPITest::TestGetTailoredSet()
1754 const char *tests
[20];
1757 { "&a < \\u212b", { "\\u212b", "A\\u030a", "\\u00c5" }, 3},
1758 { "& S < \\u0161 <<< \\u0160", { "\\u0161", "s\\u030C", "\\u0160", "S\\u030C" }, 4}
1761 uint32_t i
= 0, j
= 0;
1762 UErrorCode status
= U_ZERO_ERROR
;
1764 RuleBasedCollator
*coll
= NULL
;
1766 UnicodeSet
*set
= NULL
;
1768 for(i
= 0; i
< sizeof(setTest
)/sizeof(setTest
[0]); i
++) {
1769 buff
= UnicodeString(setTest
[i
].rules
, "").unescape();
1770 coll
= new RuleBasedCollator(buff
, status
);
1771 if(U_SUCCESS(status
)) {
1772 set
= coll
->getTailoredSet(status
);
1773 if(set
->size() != setTest
[i
].testsize
) {
1774 errln("Tailored set size different (%d) than expected (%d)", set
->size(), setTest
[i
].testsize
);
1776 for(j
= 0; j
< (uint32_t)setTest
[i
].testsize
; j
++) {
1777 buff
= UnicodeString(setTest
[i
].tests
[j
], "").unescape();
1778 if(!set
->contains(buff
)) {
1779 errln("Tailored set doesn't contain %s... It should", setTest
[i
].tests
[j
]);
1784 errln("Couldn't open collator with rules %s\n", setTest
[i
].rules
);
1790 void CollationAPITest::TestUClassID()
1792 char id
= *((char *)RuleBasedCollator::getStaticClassID());
1794 errln("Static class id for RuleBasedCollator should be 0");
1796 UErrorCode status
= U_ZERO_ERROR
;
1797 RuleBasedCollator
*coll
1798 = (RuleBasedCollator
*)Collator::createInstance(status
);
1799 if(U_FAILURE(status
)) {
1801 errln("Collator creation failed with %s", u_errorName(status
));
1804 id
= *((char *)coll
->getDynamicClassID());
1806 errln("Dynamic class id for RuleBasedCollator should be 0");
1808 id
= *((char *)CollationKey::getStaticClassID());
1810 errln("Static class id for CollationKey should be 0");
1812 CollationKey
*key
= new CollationKey();
1813 id
= *((char *)key
->getDynamicClassID());
1815 errln("Dynamic class id for CollationKey should be 0");
1817 id
= *((char *)CollationElementIterator::getStaticClassID());
1819 errln("Static class id for CollationElementIterator should be 0");
1821 UnicodeString
str("testing");
1822 CollationElementIterator
*iter
= coll
->createCollationElementIterator(str
);
1823 id
= *((char *)iter
->getDynamicClassID());
1825 errln("Dynamic class id for CollationElementIterator should be 0");
1832 class TestCollator
: public Collator
1835 virtual Collator
* clone(void) const;
1837 // dang, markus says we can't use 'using' in ICU. I hate doing this for
1838 // deprecated methods...
1840 // using Collator::compare;
1842 virtual EComparisonResult
compare(const UnicodeString
& source
,
1843 const UnicodeString
& target
) const
1845 return Collator::compare(source
, target
);
1848 virtual EComparisonResult
compare(const UnicodeString
& source
,
1849 const UnicodeString
& target
,
1850 int32_t length
) const
1852 return Collator::compare(source
, target
, length
);
1855 virtual EComparisonResult
compare(const UChar
* source
,
1856 int32_t sourceLength
,
1857 const UChar
* target
,
1858 int32_t targetLength
) const
1860 return Collator::compare(source
, sourceLength
, target
, targetLength
);
1864 virtual UCollationResult
compare(const UnicodeString
& source
,
1865 const UnicodeString
& target
,
1866 UErrorCode
& status
) const;
1867 virtual UCollationResult
compare(const UnicodeString
& source
,
1868 const UnicodeString
& target
,
1870 UErrorCode
& status
) const;
1871 virtual UCollationResult
compare(const UChar
* source
,
1872 int32_t sourceLength
,
1873 const UChar
* target
,
1874 int32_t targetLength
,
1875 UErrorCode
& status
) const;
1876 virtual CollationKey
& getCollationKey(const UnicodeString
& source
,
1878 UErrorCode
& status
) const;
1879 virtual CollationKey
& getCollationKey(const UChar
*source
,
1880 int32_t sourceLength
,
1882 UErrorCode
& status
) const;
1883 virtual int32_t hashCode(void) const;
1884 virtual const Locale
getLocale(ULocDataLocaleType type
,
1885 UErrorCode
& status
) const;
1886 virtual ECollationStrength
getStrength(void) const;
1887 virtual void setStrength(ECollationStrength newStrength
);
1888 virtual UClassID
getDynamicClassID(void) const;
1889 virtual void getVersion(UVersionInfo info
) const;
1890 virtual void setAttribute(UColAttribute attr
, UColAttributeValue value
,
1891 UErrorCode
&status
);
1892 virtual UColAttributeValue
getAttribute(UColAttribute attr
,
1893 UErrorCode
&status
);
1894 virtual uint32_t setVariableTop(const UChar
*varTop
, int32_t len
,
1895 UErrorCode
&status
);
1896 virtual uint32_t setVariableTop(const UnicodeString varTop
,
1897 UErrorCode
&status
);
1898 virtual void setVariableTop(const uint32_t varTop
, UErrorCode
&status
);
1899 virtual uint32_t getVariableTop(UErrorCode
&status
) const;
1900 virtual Collator
* safeClone(void);
1901 virtual int32_t getSortKey(const UnicodeString
& source
,
1903 int32_t resultLength
) const;
1904 virtual int32_t getSortKey(const UChar
*source
, int32_t sourceLength
,
1905 uint8_t*result
, int32_t resultLength
) const;
1906 virtual UnicodeSet
*getTailoredSet(UErrorCode
&status
) const;
1907 virtual UBool
operator!=(const Collator
& other
) const;
1908 virtual void setLocales(const Locale
& requestedLocale
, const Locale
& validLocale
);
1909 TestCollator() : Collator() {};
1910 TestCollator(UCollationStrength collationStrength
,
1911 UNormalizationMode decompositionMode
) : Collator(collationStrength
, decompositionMode
) {};
1914 inline UBool
TestCollator::operator!=(const Collator
& other
) const {
1915 return Collator::operator!=(other
);
1918 #define returnEComparisonResult(data) \
1919 if (data < 0) return Collator::LESS;\
1920 if (data > 0) return Collator::GREATER;\
1921 return Collator::EQUAL;
1923 Collator
* TestCollator::clone() const
1925 return new TestCollator();
1928 UCollationResult
TestCollator::compare(const UnicodeString
& source
,
1929 const UnicodeString
& target
,
1930 UErrorCode
& status
) const
1932 if(U_SUCCESS(status
)) {
1933 return UCollationResult(source
.compare(target
));
1939 UCollationResult
TestCollator::compare(const UnicodeString
& source
,
1940 const UnicodeString
& target
,
1942 UErrorCode
& status
) const
1944 if(U_SUCCESS(status
)) {
1945 return UCollationResult(source
.compare(0, length
, target
));
1951 UCollationResult
TestCollator::compare(const UChar
* source
,
1952 int32_t sourceLength
,
1953 const UChar
* target
,
1954 int32_t targetLength
,
1955 UErrorCode
& status
) const
1957 UnicodeString
s(source
, sourceLength
);
1958 UnicodeString
t(target
, targetLength
);
1959 return compare(s
, t
, status
);
1962 CollationKey
& TestCollator::getCollationKey(const UnicodeString
& source
,
1964 UErrorCode
& status
) const
1968 length
= source
.extract(temp
, length
, NULL
, status
);
1970 CollationKey
tempkey((uint8_t*)temp
, length
);
1975 CollationKey
& TestCollator::getCollationKey(const UChar
*source
,
1976 int32_t sourceLength
,
1978 UErrorCode
& status
) const
1980 //s tack allocation used since collationkey does not keep the unicodestring
1981 UnicodeString
str(source
, sourceLength
);
1982 return getCollationKey(str
, key
, status
);
1985 int32_t TestCollator::getSortKey(const UnicodeString
& source
, uint8_t* result
,
1986 int32_t resultLength
) const
1988 UErrorCode status
= U_ZERO_ERROR
;
1989 int32_t length
= source
.extract((char *)result
, resultLength
, NULL
,
1995 int32_t TestCollator::getSortKey(const UChar
*source
, int32_t sourceLength
,
1996 uint8_t*result
, int32_t resultLength
) const
1998 UnicodeString
str(source
, sourceLength
);
1999 return getSortKey(str
, result
, resultLength
);
2002 int32_t TestCollator::hashCode() const
2007 const Locale
TestCollator::getLocale(ULocDataLocaleType type
,
2008 UErrorCode
& status
) const
2010 // api not used, this is to make the compiler happy
2011 if (U_FAILURE(status
)) {
2012 type
= ULOC_DATA_LOCALE_TYPE_LIMIT
;
2017 Collator::ECollationStrength
TestCollator::getStrength() const
2022 void TestCollator::setStrength(Collator::ECollationStrength newStrength
)
2024 // api not used, this is to make the compiler happy
2025 newStrength
= TERTIARY
;
2028 UClassID
TestCollator::getDynamicClassID(void) const
2033 void TestCollator::getVersion(UVersionInfo info
) const
2035 // api not used, this is to make the compiler happy
2036 memset(info
, 0, U_MAX_VERSION_LENGTH
);
2039 void TestCollator::setAttribute(UColAttribute attr
, UColAttributeValue value
,
2042 // api not used, this is to make the compiler happy
2043 if (U_FAILURE(status
)) {
2044 attr
= UCOL_ATTRIBUTE_COUNT
;
2049 UColAttributeValue
TestCollator::getAttribute(UColAttribute attr
,
2052 // api not used, this is to make the compiler happy
2053 if (U_FAILURE(status
) || attr
== UCOL_ATTRIBUTE_COUNT
) {
2056 return UCOL_DEFAULT
;
2059 uint32_t TestCollator::setVariableTop(const UChar
*varTop
, int32_t len
,
2062 // api not used, this is to make the compiler happy
2063 if (U_SUCCESS(status
) && (varTop
== 0 || len
< -1)) {
2064 status
= U_ILLEGAL_ARGUMENT_ERROR
;
2069 uint32_t TestCollator::setVariableTop(const UnicodeString varTop
,
2072 // api not used, this is to make the compiler happy
2073 if (U_SUCCESS(status
) && varTop
.length() == 0) {
2074 status
= U_ILLEGAL_ARGUMENT_ERROR
;
2079 void TestCollator::setVariableTop(const uint32_t varTop
, UErrorCode
&status
)
2081 // api not used, this is to make the compiler happy
2082 if (U_SUCCESS(status
) && varTop
== 0) {
2083 status
= U_ILLEGAL_ARGUMENT_ERROR
;
2087 uint32_t TestCollator::getVariableTop(UErrorCode
&status
) const
2090 // api not used, this is to make the compiler happy
2091 if (U_SUCCESS(status
)) {
2094 return (uint32_t)(0xFFFFFFFFu
);
2097 Collator
* TestCollator::safeClone(void)
2099 return new TestCollator();
2102 UnicodeSet
* TestCollator::getTailoredSet(UErrorCode
&status
) const
2104 return Collator::getTailoredSet(status
);
2107 void TestCollator::setLocales(const Locale
& requestedLocale
, const Locale
& validLocale
)
2109 Collator::setLocales(requestedLocale
, validLocale
);
2113 void CollationAPITest::TestSubclass()
2117 doAssert(col1
!= col2
, "2 instance of TestCollator should be different");
2118 if (col1
.hashCode() != col2
.hashCode()) {
2119 errln("Every TestCollator has the same hashcode");
2121 UnicodeString
abc("abc", 3);
2122 UnicodeString
bcd("bcd", 3);
2123 if (col1
.compare(abc
, bcd
) != abc
.compare(bcd
)) {
2124 errln("TestCollator compare should be the same as the default "
2125 "string comparison");
2128 UErrorCode status
= U_ZERO_ERROR
;
2129 col1
.getCollationKey(abc
, key
, status
);
2131 const char* bytes
= (const char *)key
.getByteArray(length
);
2132 UnicodeString
keyarray(bytes
, length
, NULL
, status
);
2133 if (abc
!= keyarray
) {
2134 errln("TestCollator collationkey API is returning wrong values");
2137 UnicodeSet
expectedset(0, 0x10FFFF);
2138 UnicodeSet
*defaultset
= col1
.getTailoredSet(status
);
2139 if (!defaultset
->containsAll(expectedset
)
2140 || !expectedset
.containsAll(*defaultset
)) {
2141 errln("Error: expected default tailoring to be 0 to 0x10ffff");
2145 // use base class implementation
2146 Locale loc1
= Locale::getGermany();
2147 Locale loc2
= Locale::getFrance();
2148 col1
.setLocales(loc1
, loc2
); // default implementation has no effect
2150 UnicodeString displayName
;
2151 col1
.getDisplayName(loc1
, loc2
, displayName
); // de_DE collator in fr_FR locale
2153 TestCollator
col3(UCOL_TERTIARY
, UNORM_NONE
);
2154 UnicodeString
a("a");
2155 UnicodeString
b("b");
2156 Collator::EComparisonResult result
= Collator::EComparisonResult(a
.compare(b
));
2157 if(col1
.compare(a
, b
) != result
) {
2158 errln("Collator doesn't give default result");
2160 if(col1
.compare(a
, b
, 1) != result
) {
2161 errln("Collator doesn't give default result");
2163 if(col1
.compare(a
.getBuffer(), a
.length(), b
.getBuffer(), b
.length()) != result
) {
2164 errln("Collator doesn't give default result");
2168 void CollationAPITest::TestNULLCharTailoring()
2170 UErrorCode status
= U_ZERO_ERROR
;
2171 UChar buf
[256] = {0};
2172 int32_t len
= u_unescape("&a < '\\u0000'", buf
, 256);
2173 UnicodeString
first((UChar
)0x0061);
2174 UnicodeString
second((UChar
)0);
2175 RuleBasedCollator
*coll
= new RuleBasedCollator(UnicodeString(buf
, len
), status
);
2176 if(U_FAILURE(status
)) {
2177 errln("Failed to open collator");
2179 UCollationResult res
= coll
->compare(first
, second
, status
);
2180 if(res
!= UCOL_LESS
) {
2181 errln("a should be less then NULL after tailoring");
2186 void CollationAPITest::TestClone() {
2188 UErrorCode status
= U_ZERO_ERROR
;
2189 RuleBasedCollator
* c0
= (RuleBasedCollator
*)Collator::createInstance(status
);
2190 c0
->setStrength(Collator::TERTIARY
);
2191 dump("c0", c0
, status
);
2194 RuleBasedCollator
* c1
= (RuleBasedCollator
*)Collator::createInstance(status
);
2195 c1
->setStrength(Collator::TERTIARY
);
2196 UColAttributeValue val
= c1
->getAttribute(UCOL_CASE_FIRST
, status
);
2197 if(val
== UCOL_LOWER_FIRST
){
2198 c1
->setAttribute(UCOL_CASE_FIRST
, UCOL_UPPER_FIRST
, status
);
2200 c1
->setAttribute(UCOL_CASE_FIRST
, UCOL_LOWER_FIRST
, status
);
2202 dump("c0", c0
, status
);
2203 dump("c1", c1
, status
);
2206 RuleBasedCollator
* c2
= (RuleBasedCollator
*)c1
->clone();
2207 val
= c2
->getAttribute(UCOL_CASE_FIRST
, status
);
2208 if(val
== UCOL_LOWER_FIRST
){
2209 c2
->setAttribute(UCOL_CASE_FIRST
, UCOL_UPPER_FIRST
, status
);
2211 c2
->setAttribute(UCOL_CASE_FIRST
, UCOL_LOWER_FIRST
, status
);
2213 if(U_FAILURE(status
)){
2214 errln("set and get attributes of collator failed. %s\n", u_errorName(status
));
2217 dump("c0", c0
, status
);
2218 dump("c1", c1
, status
);
2219 dump("c2", c2
, status
);
2221 errln("The cloned objects refer to same data");
2228 void CollationAPITest::dump(UnicodeString msg
, RuleBasedCollator
* c
, UErrorCode
& status
) {
2229 const char* bigone
= "One";
2230 const char* littleone
= "one";
2232 logln(msg
+ " " + c
->compare(bigone
, littleone
) +
2233 " s: " + c
->getStrength() +
2234 " u: " + c
->getAttribute(UCOL_CASE_FIRST
, status
));
2236 void CollationAPITest::runIndexedTest( int32_t index
, UBool exec
, const char* &name
, char* /*par */)
2238 if (exec
) logln("TestSuite CollationAPITest: ");
2240 case 0: name
= "TestProperty"; if (exec
) TestProperty(/* par */); break;
2241 case 1: name
= "TestOperators"; if (exec
) TestOperators(/* par */); break;
2242 case 2: name
= "TestDuplicate"; if (exec
) TestDuplicate(/* par */); break;
2243 case 3: name
= "TestCompare"; if (exec
) TestCompare(/* par */); break;
2244 case 4: name
= "TestHashCode"; if (exec
) TestHashCode(/* par */); break;
2245 case 5: name
= "TestCollationKey"; if (exec
) TestCollationKey(/* par */); break;
2246 case 6: name
= "TestElemIter"; if (exec
) TestElemIter(/* par */); break;
2247 case 7: name
= "TestGetAll"; if (exec
) TestGetAll(/* par */); break;
2248 case 8: name
= "TestRuleBasedColl"; if (exec
) TestRuleBasedColl(/* par */); break;
2249 case 9: name
= "TestDecomposition"; if (exec
) TestDecomposition(/* par */); break;
2250 case 10: name
= "TestSafeClone"; if (exec
) TestSafeClone(/* par */); break;
2251 case 11: name
= "TestSortKey"; if (exec
) TestSortKey(); break;
2252 case 12: name
= "TestMaxExpansion"; if (exec
) TestMaxExpansion(); break;
2253 case 13: name
= "TestDisplayName"; if (exec
) TestDisplayName(); break;
2254 case 14: name
= "TestAttribute"; if (exec
) TestAttribute(); break;
2255 case 15: name
= "TestVariableTopSetting"; if (exec
) TestVariableTopSetting(); break;
2256 case 16: name
= "TestRules"; if (exec
) TestRules(); break;
2257 case 17: name
= "TestGetLocale"; if (exec
) TestGetLocale(); break;
2258 case 18: name
= "TestBounds"; if (exec
) TestBounds(); break;
2259 case 19: name
= "TestGetTailoredSet"; if (exec
) TestGetTailoredSet(); break;
2260 case 20: name
= "TestUClassID"; if (exec
) TestUClassID(); break;
2261 case 21: name
= "TestSubclass"; if (exec
) TestSubclass(); break;
2262 case 22: name
= "TestNULLCharTailoring"; if (exec
) TestNULLCharTailoring(); break;
2263 case 23: name
= "TestClone"; if (exec
) TestClone(); break;
2264 default: name
= ""; break;
2268 #endif /* #if !UCONFIG_NO_COLLATION */