Path: blob/aarch64-shenandoah-jdk8u272-b10/jdk/test/java/lang/StringBuffer/Supplementary.java
38812 views
/*1* Copyright (c) 2003, 2010, Oracle and/or its affiliates. All rights reserved.2* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.3*4* This code is free software; you can redistribute it and/or modify it5* under the terms of the GNU General Public License version 2 only, as6* published by the Free Software Foundation.7*8* This code is distributed in the hope that it will be useful, but WITHOUT9* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or10* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License11* version 2 for more details (a copy is included in the LICENSE file that12* accompanied this code).13*14* You should have received a copy of the GNU General Public License version15* 2 along with this work; if not, write to the Free Software Foundation,16* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.17*18* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA19* or visit www.oracle.com if you need additional information or have any20* questions.21*/2223/*24*25* @test26* @bug 4533872 4915683 4985217 5017280 693711227* @summary Unit tests for supplementary character support (JSR-204)28*/2930public class Supplementary {3132public static void main(String[] args) {33test1(); // Test for codePointAt(int index)34test2(); // Test for codePointBefore(int index)35test3(); // Test for reverse()36test4(); // Test for appendCodePoint(int codePoint)37test5(); // Test for codePointCount(int beginIndex, int endIndex)38test6(); // Test for offsetByCodePoints(int index, int offset)39}4041/* Text strings which are used as input data.42* The comment above each text string means the index of each 16-bit char43* for convenience.44*/45static final String[] input = {46/* 111 1 111111 22222470123 4 5678 9 012 3 456789 01234 */48"abc\uD800\uDC00def\uD800\uD800ab\uD800\uDC00cdefa\uDC00bcdef",49/* 1 1111 1111 1 222500 12345 6789 0 1234 5678 9 012 */51"\uD800defg\uD800hij\uD800\uDC00klm\uDC00nop\uDC00\uD800rt\uDC00",52/* 11 1 1111 1 112 222530 12345 6 78901 2 3456 7 890 123 */54"\uDC00abcd\uDBFF\uDFFFefgh\uD800\uDC009ik\uDC00\uDC00lm\uDC00no\uD800",55/* 111 111111 1 22 2560 1 2345 678 9 012 345678 9 01 2 */57"\uD800\uDC00!#$\uD800%&\uD800\uDC00;+\uDC00<>;=^\uDC00\\@\uD800\uDC00",5859// includes an undefined supplementary character in Unicode 4.0.060/* 1 11 1 1111 1610 1 2345 6 789 0 12 3 4567 8 */62"\uDB40\uDE00abc\uDE01\uDB40de\uDB40\uDE02f\uDB40\uDE03ghi\uDB40\uDE02",63};646566/* Expected results for:67* test1(): for codePointAt()68*69* Each character in each array is the golden data for each text string70* in the above input data. For example, the first data in each array is71* for the first input string.72*/73static final int[][] golden1 = {74{'a', 0xD800, 0xDC00, 0x10000, 0xE0200}, // codePointAt(0)75{0xD800, 0x10000, 'g', 0xDC00, 0xE0202}, // codePointAt(9)76{'f', 0xDC00, 0xD800, 0xDC00, 0xDE02}, // codePointAt(length-1)77};7879/*80* Test for codePointAt(int index) method81*/82static void test1() {8384for (int i = 0; i < input.length; i++) {85StringBuffer sb = new StringBuffer(input[i]);8687/*88* Normal case89*/90testCodePoint(At, sb, 0, golden1[0][i]);91testCodePoint(At, sb, 9, golden1[1][i]);92testCodePoint(At, sb, sb.length()-1, golden1[2][i]);9394/*95* Abnormal case - verify that an exception is thrown.96*/97testCodePoint(At, sb, -1);98testCodePoint(At, sb, sb.length());99}100}101102103/* Expected results for:104* test2(): for codePointBefore()105*106* Each character in each array is the golden data for each text string107* in the above input data. For example, the first data in each array is108* for the first input string.109*/110static final int[][] golden2 = {111{'a', 0xD800, 0xDC00, 0xD800, 0xDB40}, // codePointBefore(1)112{0xD800, 'l', 0x10000, 0xDC00, 0xDB40}, // codePointBefore(13)113{'f', 0xDC00, 0xD800, 0x10000, 0xE0202}, // codePointBefore(length)114};115116/*117* Test for codePointBefore(int index) method118*/119static void test2() {120121for (int i = 0; i < input.length; i++) {122StringBuffer sb = new StringBuffer(input[i]);123124/*125* Normal case126*/127testCodePoint(Before, sb, 1, golden2[0][i]);128testCodePoint(Before, sb, 13, golden2[1][i]);129testCodePoint(Before, sb, sb.length(), golden2[2][i]);130131/*132* Abnormal case - verify that an exception is thrown.133*/134testCodePoint(Before, sb, 0);135testCodePoint(Before, sb, sb.length()+1);136}137}138139140/* Expected results for:141* test3(): for reverse()142*143* Unlike golden1 and golden2, each array is the golden data for each text144* string in the above input data. For example, the first array is for145* the first input string.146*/147static final String[] golden3 = {148"fedcb\uDC00afedc\uD800\uDC00ba\uD800\uD800fed\uD800\uDC00cba",149"\uDC00tr\uD800\uDC00pon\uDC00mlk\uD800\uDC00jih\uD800gfed\uD800",150"\uD800on\uDC00ml\uDC00\uDC00ki9\uD800\uDC00hgfe\uDBFF\uDFFFdcba\uDC00",151"\uD800\uDC00@\\\uDC00^=;><\uDC00+;\uD800\uDC00&%\uD800$#!\uD800\uDC00",152153// includes an undefined supplementary character in Unicode 4.0.0154"\uDB40\uDE02ihg\uDB40\uDE03f\uDB40\uDE02ed\uDB40\uDE01cba\uDB40\uDE00",155};156157// Additional input data & expected result for test3()158static final String[][] testdata1 = {159{"a\uD800\uDC00", "\uD800\uDC00a"},160{"a\uDC00\uD800", "\uD800\uDC00a"},161{"\uD800\uDC00a", "a\uD800\uDC00"},162{"\uDC00\uD800a", "a\uD800\uDC00"},163{"\uDC00\uD800\uD801", "\uD801\uD800\uDC00"},164{"\uDC00\uD800\uDC01", "\uD800\uDC01\uDC00"},165{"\uD801\uD800\uDC00", "\uD800\uDC00\uD801"},166{"\uD800\uDC01\uDC00", "\uDC00\uD800\uDC01"},167{"\uD800\uDC00\uDC01\uD801", "\uD801\uDC01\uD800\uDC00"},168};169170/*171* Test for reverse() method172*/173static void test3() {174for (int i = 0; i < input.length; i++) {175StringBuffer sb = new StringBuffer(input[i]).reverse();176177check(!golden3[i].equals(new String(sb)),178"reverse() for <" + toHexString(input[i]) + ">",179sb, golden3[i]);180}181182for (int i = 0; i < testdata1.length; i++) {183StringBuffer sb = new StringBuffer(testdata1[i][0]).reverse();184185check(!testdata1[i][1].equals(new String(sb)),186"reverse() for <" + toHexString(testdata1[i][0]) + ">",187sb, testdata1[i][1]);188}189}190191/**192* Test for appendCodePoint() method193*/194static void test4() {195for (int i = 0; i < input.length; i++) {196String s = input[i];197StringBuffer sb = new StringBuffer();198int c;199for (int j = 0; j < s.length(); j += Character.charCount(c)) {200c = s.codePointAt(j);201StringBuffer rsb = sb.appendCodePoint(c);202check(sb != rsb, "appendCodePoint returned a wrong object");203int sbc = sb.codePointAt(j);204check(sbc != c, "appendCodePoint(j) != c", sbc, c);205}206check(!s.equals(sb.toString()),207"appendCodePoint() produced a wrong result with input["+i+"]");208}209210// test exception211testAppendCodePoint(-1, IllegalArgumentException.class);212testAppendCodePoint(Character.MAX_CODE_POINT+1, IllegalArgumentException.class);213}214215/**216* Test codePointCount(int, int)217*218* This test case assumes that219* Character.codePointCount(CharSequence, int, int) works220* correctly.221*/222static void test5() {223for (int i = 0; i < input.length; i++) {224String s = input[i];225StringBuffer sb = new StringBuffer(s);226int length = sb.length();227for (int j = 0; j <= length; j++) {228int result = sb.codePointCount(j, length);229int expected = Character.codePointCount(sb, j, length);230check(result != expected, "codePointCount(input["+i+"], "+j+", "+length+")",231result, expected);232}233for (int j = length; j >= 0; j--) {234int result = sb.codePointCount(0, j);235int expected = Character.codePointCount(sb, 0, j);236check(result != expected, "codePointCount(input["+i+"], 0, "+j+")",237result, expected);238}239240// test exceptions241testCodePointCount(null, 0, 0, NullPointerException.class);242testCodePointCount(sb, -1, length, IndexOutOfBoundsException.class);243testCodePointCount(sb, 0, length+1, IndexOutOfBoundsException.class);244testCodePointCount(sb, length, length-1, IndexOutOfBoundsException.class);245}246}247248/**249* Test offsetByCodePoints(int, int)250*251* This test case assumes that252* Character.codePointCount(CharSequence, int, int) works253* correctly.254*/255static void test6() {256for (int i = 0; i < input.length; i++) {257String s = input[i];258StringBuffer sb = new StringBuffer(s);259int length = s.length();260for (int j = 0; j <= length; j++) {261int nCodePoints = Character.codePointCount(sb, j, length);262int result = sb.offsetByCodePoints(j, nCodePoints);263check(result != length,264"offsetByCodePoints(input["+i+"], "+j+", "+nCodePoints+")",265result, length);266result = sb.offsetByCodePoints(length, -nCodePoints);267int expected = j;268if (j > 0 && j < length) {269int cp = sb.codePointBefore(j+1);270if (Character.isSupplementaryCodePoint(cp)) {271expected--;272}273}274check(result != expected,275"offsetByCodePoints(input["+i+"], "+j+", "+(-nCodePoints)+")",276result, expected);277}278for (int j = length; j >= 0; j--) {279int nCodePoints = Character.codePointCount(sb, 0, j);280int result = sb.offsetByCodePoints(0, nCodePoints);281int expected = j;282if (j > 0 && j < length) {283int cp = sb.codePointAt(j-1);284if (Character.isSupplementaryCodePoint(cp)) {285expected++;286}287}288check(result != expected,289"offsetByCodePoints(input["+i+"], 0, "+nCodePoints+")",290result, expected);291result = sb.offsetByCodePoints(j, -nCodePoints);292check(result != 0,293"offsetBycodePoints(input["+i+"], "+j+", "+(-nCodePoints)+")",294result, 0);295}296297// test exceptions298testOffsetByCodePoints(null, 0, 0, NullPointerException.class);299testOffsetByCodePoints(sb, -1, length, IndexOutOfBoundsException.class);300testOffsetByCodePoints(sb, 0, length+1, IndexOutOfBoundsException.class);301testOffsetByCodePoints(sb, 1, -2, IndexOutOfBoundsException.class);302testOffsetByCodePoints(sb, length, length-1, IndexOutOfBoundsException.class);303testOffsetByCodePoints(sb, length, -(length+1), IndexOutOfBoundsException.class);304}305}306307308static final boolean At = true, Before = false;309310static void testCodePoint(boolean isAt, StringBuffer sb, int index, int expected) {311int c = isAt ? sb.codePointAt(index) : sb.codePointBefore(index);312313check(c != expected,314"codePoint" + (isAt ? "At" : "Before") + "(" + index + ") for <"315+ sb + ">", c, expected);316}317318static void testCodePoint(boolean isAt, StringBuffer sb, int index) {319boolean exceptionOccurred = false;320321try {322int c = isAt ? sb.codePointAt(index) : sb.codePointBefore(index);323}324catch (StringIndexOutOfBoundsException e) {325exceptionOccurred = true;326}327check(!exceptionOccurred,328"codePoint" + (isAt ? "At" : "Before") + "(" + index + ") for <"329+ sb + "> should throw StringIndexOutOfBoundsPointerException.");330}331332static void testAppendCodePoint(int codePoint, Class expectedException) {333try {334new StringBuffer().appendCodePoint(codePoint);335} catch (Exception e) {336if (expectedException.isInstance(e)) {337return;338}339throw new RuntimeException("Error: Unexpected exception", e);340}341check(true, "appendCodePoint(" + toHexString(codePoint) + ") didn't throw "342+ expectedException.getName());343}344345static void testCodePointCount(StringBuffer sb, int beginIndex, int endIndex,346Class expectedException) {347try {348int n = sb.codePointCount(beginIndex, endIndex);349} catch (Exception e) {350if (expectedException.isInstance(e)) {351return;352}353throw new RuntimeException("Error: Unexpected exception", e);354}355check(true, "codePointCount() didn't throw " + expectedException.getName());356}357358static void testOffsetByCodePoints(StringBuffer sb, int index, int offset,359Class expectedException) {360try {361int n = sb.offsetByCodePoints(index, offset);362} catch (Exception e) {363if (expectedException.isInstance(e)) {364return;365}366throw new RuntimeException("Error: Unexpected exception", e);367}368check(true, "offsetByCodePoints() didn't throw " + expectedException.getName());369}370371static void check(boolean err, String msg) {372if (err) {373throw new RuntimeException("Error: " + msg);374}375}376377static void check(boolean err, String s, int got, int expected) {378if (err) {379throw new RuntimeException("Error: " + s380+ " returned an unexpected value. got "381+ toHexString(got)382+ ", expected "383+ toHexString(expected));384}385}386387static void check(boolean err, String s, StringBuffer got, String expected) {388if (err) {389throw new RuntimeException("Error: " + s390+ " returned an unexpected value. got <"391+ toHexString(new String(got))392+ ">, expected <"393+ toHexString(expected)394+ ">");395}396}397398private static String toHexString(int c) {399return "0x" + Integer.toHexString(c);400}401402private static String toHexString(String s) {403StringBuffer sb = new StringBuffer();404for (int i = 0; i < s.length(); i++) {405char c = s.charAt(i);406407sb.append(" 0x");408if (c < 0x10) sb.append('0');409if (c < 0x100) sb.append('0');410if (c < 0x1000) sb.append('0');411sb.append(Integer.toHexString(c));412}413sb.append(' ');414return sb.toString();415}416}417418419