github.com/enetx/g@v1.0.80/tests/string_test.go (about) 1 package g_test 2 3 import ( 4 "io" 5 "reflect" 6 "testing" 7 "unicode" 8 9 "github.com/enetx/g" 10 ) 11 12 func TestStringBuilder(t *testing.T) { 13 // Create a String 14 str := g.NewString("hello") 15 16 // Call the Builder method 17 builder := str.Builder() 18 19 // Check if the Builder has been properly initialized 20 expected := "hello" 21 if result := builder.String().Std(); result != expected { 22 t.Errorf("Builder() = %s; want %s", result, expected) 23 } 24 } 25 26 func TestStringMinMax(t *testing.T) { 27 // Test cases for Min method 28 minTestCases := []struct { 29 inputs []g.String 30 expected g.String 31 }{ 32 {[]g.String{"apple", "banana", "orange"}, "apple"}, 33 {[]g.String{"cat", "dog", "elephant"}, "cat"}, 34 {[]g.String{"123", "456", "789"}, "123"}, 35 } 36 37 for _, testCase := range minTestCases { 38 result := g.NewString(testCase.inputs[0]).Min(testCase.inputs[1:]...) 39 if result != testCase.expected { 40 t.Errorf("Min test failed. Expected: %s, Got: %s", testCase.expected, result) 41 } 42 } 43 44 // Test cases for Max method 45 maxTestCases := []struct { 46 inputs []g.String 47 expected g.String 48 }{ 49 {[]g.String{"apple", "banana", "orange"}, "orange"}, 50 {[]g.String{"cat", "dog", "elephant"}, "elephant"}, 51 {[]g.String{"123", "456", "789"}, "789"}, 52 } 53 54 for _, testCase := range maxTestCases { 55 result := g.NewString(testCase.inputs[0]).Max(testCase.inputs[1:]...) 56 if result != testCase.expected { 57 t.Errorf("Max test failed. Expected: %s, Got: %s", testCase.expected, result) 58 } 59 } 60 } 61 62 func TestChars(t *testing.T) { 63 // Testing on a regular string with ASCII characters 64 asciiStr := g.String("Hello") 65 asciiExpected := g.Slice[g.String]{"H", "e", "l", "l", "o"} 66 asciiResult := asciiStr.Chars().Collect() 67 if !reflect.DeepEqual(asciiExpected, asciiResult) { 68 t.Errorf("Expected %v, but got %v", asciiExpected, asciiResult) 69 } 70 71 // Testing on a string with Unicode characters (Russian) 72 unicodeStr := g.String("Привет") 73 unicodeExpected := g.Slice[g.String]{"П", "р", "и", "в", "е", "т"} 74 unicodeResult := unicodeStr.Chars().Collect() 75 if !reflect.DeepEqual(unicodeExpected, unicodeResult) { 76 t.Errorf("Expected %v, but got %v", unicodeExpected, unicodeResult) 77 } 78 79 // Testing on a string with Unicode characters (Chinese) 80 chineseStr := g.String("你好") 81 chineseExpected := g.Slice[g.String]{"你", "好"} 82 chineseResult := chineseStr.Chars().Collect() 83 if !reflect.DeepEqual(chineseExpected, chineseResult) { 84 t.Errorf("Expected %v, but got %v", chineseExpected, chineseResult) 85 } 86 87 // Additional test with a mix of ASCII and Unicode characters 88 mixedStr := g.String("Hello 你好") 89 mixedExpected := g.Slice[g.String]{"H", "e", "l", "l", "o", " ", "你", "好"} 90 mixedResult := mixedStr.Chars().Collect() 91 if !reflect.DeepEqual(mixedExpected, mixedResult) { 92 t.Errorf("Expected %v, but got %v", mixedExpected, mixedResult) 93 } 94 95 // Testing on a string with special characters and symbols 96 specialStr := g.String("Hello, 你好! How are you today? こんにちは") 97 specialExpected := g.Slice[g.String]{ 98 "H", 99 "e", 100 "l", 101 "l", 102 "o", 103 ",", 104 " ", 105 "你", 106 "好", 107 "!", 108 " ", 109 "H", 110 "o", 111 "w", 112 " ", 113 "a", 114 "r", 115 "e", 116 " ", 117 "y", 118 "o", 119 "u", 120 " ", 121 "t", 122 "o", 123 "d", 124 "a", 125 "y", 126 "?", 127 " ", 128 "こ", 129 "ん", 130 "に", 131 "ち", 132 "は", 133 } 134 specialResult := specialStr.Chars().Collect() 135 if !reflect.DeepEqual(specialExpected, specialResult) { 136 t.Errorf("Expected %v, but got %v", specialExpected, specialResult) 137 } 138 139 // Testing on a string with emojis 140 emojiStr := g.String("Hello, 😊🌍🚀") 141 emojiExpected := g.Slice[g.String]{"H", "e", "l", "l", "o", ",", " ", "😊", "🌍", "🚀"} 142 emojiResult := emojiStr.Chars().Collect() 143 if !reflect.DeepEqual(emojiExpected, emojiResult) { 144 t.Errorf("Expected %v, but got %v", emojiExpected, emojiResult) 145 } 146 147 // Testing on an empty string 148 emptyStr := g.String("") 149 emptyExpected := g.Slice[g.String]{} 150 emptyResult := emptyStr.Chars().Collect() 151 if !reflect.DeepEqual(emptyExpected, emptyResult) { 152 t.Errorf("Expected %v, but got %v", emptyExpected, emptyResult) 153 } 154 } 155 156 func TestStringIsDigit(t *testing.T) { 157 tests := []struct { 158 name string 159 str g.String 160 want bool 161 }{ 162 {"empty", g.String(""), false}, 163 {"one", g.String("1"), true}, 164 {"nine", g.String("99999"), true}, 165 {"non-digit", g.String("1111a"), false}, 166 } 167 168 for _, tt := range tests { 169 t.Run(tt.name, func(t *testing.T) { 170 if got := tt.str.IsDigit(); got != tt.want { 171 t.Errorf("String.IsDigit() = %v, want %v", got, tt.want) 172 } 173 }) 174 } 175 } 176 177 func TestStringToInt(t *testing.T) { 178 tests := []struct { 179 name string 180 str g.String 181 want g.Int 182 }{ 183 { 184 name: "empty", 185 str: g.String(""), 186 want: 0, 187 }, 188 { 189 name: "one digit", 190 str: g.String("1"), 191 want: 1, 192 }, 193 { 194 name: "two digits", 195 str: g.String("12"), 196 want: 12, 197 }, 198 { 199 name: "one letter", 200 str: g.String("a"), 201 want: 0, 202 }, 203 { 204 name: "one digit and one letter", 205 str: g.String("1a"), 206 want: 0, 207 }, 208 } 209 for _, tt := range tests { 210 t.Run(tt.name, func(t *testing.T) { 211 if got := tt.str.ToInt().UnwrapOrDefault(); got != tt.want { 212 t.Errorf("String.ToInt() = %v, want %v", got, tt.want) 213 } 214 }) 215 } 216 } 217 218 func TestStringToTitle(t *testing.T) { 219 tests := []struct { 220 name string 221 str g.String 222 want g.String 223 }{ 224 {"empty", "", ""}, 225 {"one word", "hello", "Hello"}, 226 {"two words", "hello world", "Hello World"}, 227 {"three words", "hello world, how are you?", "Hello World, How Are You?"}, 228 {"multiple hyphens", "foo-bar-baz", "Foo-Bar-Baz"}, 229 {"non-ascii letters", "こんにちは, 世界!", "こんにちは, 世界!"}, 230 {"all whitespace", " \t\n ", " \t\n "}, 231 {"numbers", "12345 67890", "12345 67890"}, 232 {"arabic", "مرحبا بالعالم", "مرحبا بالعالم"}, 233 {"chinese", "你好世界", "你好世界"}, 234 {"czech", "ahoj světe", "Ahoj Světe"}, 235 {"danish", "hej verden", "Hej Verden"}, 236 {"dutch", "hallo wereld", "Hallo Wereld"}, 237 {"french", "bonjour tout le monde", "Bonjour Tout Le Monde"}, 238 {"german", "hallo welt", "Hallo Welt"}, 239 {"hebrew", "שלום עולם", "שלום עולם"}, 240 {"hindi", "नमस्ते दुनिया", "नमस्ते दुनिया"}, 241 {"hungarian", "szia világ", "Szia Világ"}, 242 {"italian", "ciao mondo", "Ciao Mondo"}, 243 {"japanese", "こんにちは世界", "こんにちは世界"}, 244 {"korean", "안녕하세요 세상", "안녕하세요 세상"}, 245 {"norwegian", "hei verden", "Hei Verden"}, 246 {"polish", "witaj świecie", "Witaj Świecie"}, 247 {"portuguese", "olá mundo", "Olá Mundo"}, 248 {"russian", "привет мир", "Привет Мир"}, 249 {"spanish", "hola mundo", "Hola Mundo"}, 250 {"swedish", "hej världen", "Hej Världen"}, 251 {"turkish", "merhaba dünya", "Merhaba Dünya"}, 252 } 253 254 for _, tt := range tests { 255 t.Run(tt.name, func(t *testing.T) { 256 if got := tt.str.Title(); got.Ne(tt.want) { 257 t.Errorf("String.ToTitle() = %v, want %v", got, tt.want) 258 } 259 }) 260 } 261 } 262 263 func TestStringAdd(t *testing.T) { 264 tests := []struct { 265 name string 266 str g.String 267 s g.String 268 want g.String 269 }{ 270 { 271 name: "empty", 272 str: g.String(""), 273 s: g.String(""), 274 want: g.String(""), 275 }, 276 { 277 name: "empty_hs", 278 str: g.String(""), 279 s: g.String("test"), 280 want: g.String("test"), 281 }, 282 { 283 name: "empty_s", 284 str: g.String("test"), 285 s: g.String(""), 286 want: g.String("test"), 287 }, 288 { 289 name: "not_empty", 290 str: g.String("test"), 291 s: g.String("test"), 292 want: g.String("testtest"), 293 }, 294 } 295 296 for _, tt := range tests { 297 t.Run(tt.name, func(t *testing.T) { 298 if got := tt.str.Append(tt.s); got != tt.want { 299 t.Errorf("String.Add() = %v, want %v", got, tt.want) 300 } 301 }) 302 } 303 } 304 305 func TestStringAddPrefix(t *testing.T) { 306 tests := []struct { 307 name string 308 str g.String 309 s g.String 310 want g.String 311 }{ 312 { 313 name: "empty", 314 str: g.String(""), 315 s: g.String(""), 316 want: g.String(""), 317 }, 318 { 319 name: "empty_hs", 320 str: g.String(""), 321 s: g.String("test"), 322 want: g.String("test"), 323 }, 324 { 325 name: "empty_s", 326 str: g.String("test"), 327 s: g.String(""), 328 want: g.String("test"), 329 }, 330 { 331 name: "not_empty", 332 str: g.String("rest"), 333 s: g.String("test"), 334 want: g.String("testrest"), 335 }, 336 } 337 338 for _, tt := range tests { 339 t.Run(tt.name, func(t *testing.T) { 340 if got := tt.str.Prepend(tt.s); got != tt.want { 341 t.Errorf("String.AddPrefix() = %v, want %v", got, tt.want) 342 } 343 }) 344 } 345 } 346 347 func TestStringRandom(t *testing.T) { 348 for i := range 100 { 349 random := g.NewString("").Random(g.Int(i)) 350 351 if random.Len().Std() != i { 352 t.Errorf("Random string length %d is not equal to %d", random.Len(), i) 353 } 354 } 355 } 356 357 func TestStringChunks(t *testing.T) { 358 str := g.String("") 359 chunks := str.Chunks(3) 360 361 if chunks.Len() != 0 { 362 t.Errorf("Expected empty slice, but got %v", chunks) 363 } 364 365 str = g.String("hello") 366 chunks = str.Chunks(10) 367 368 if chunks.Len() != 1 { 369 t.Errorf("Expected 1 chunk, but got %v", chunks.Len()) 370 } 371 372 if chunks[0] != str { 373 t.Errorf("Expected chunk to be %v, but got %v", str, chunks.Get(0)) 374 } 375 376 str = g.String("hello") 377 chunks = str.Chunks(2) 378 379 if chunks.Len() != 3 { 380 t.Errorf("Expected 3 chunks, but got %v", chunks.Len()) 381 } 382 383 expectedChunks := g.Slice[g.String]{"he", "ll", "o"} 384 385 for i, c := range chunks { 386 if c != expectedChunks[i] { 387 t.Errorf("Expected chunk %v to be %v, but got %v", i, expectedChunks[i], c) 388 } 389 } 390 391 str = g.String("hello world") 392 chunks = str.Chunks(3) 393 394 if chunks.Len() != 4 { 395 t.Errorf("Expected 4 chunks, but got %v", chunks.Len()) 396 } 397 398 expectedChunks = g.Slice[g.String]{"hel", "lo ", "wor", "ld"} 399 400 for i, c := range chunks { 401 if c != expectedChunks[i] { 402 t.Errorf("Expected chunk %v to be %v, but got %v", i, expectedChunks[i], c) 403 } 404 } 405 406 str = g.String("hello") 407 chunks = str.Chunks(5) 408 409 if chunks.Len() != 1 { 410 t.Errorf("Expected 1 chunk, but got %v", chunks.Len()) 411 } 412 413 if chunks.Get(0) != str { 414 t.Errorf("Expected chunk to be %v, but got %v", str, chunks.Get(0)) 415 } 416 417 str = g.String("hello") 418 chunks = str.Chunks(-1) 419 420 if chunks.Len() != 0 { 421 t.Errorf("Expected empty slice, but got %v", chunks) 422 } 423 } 424 425 func TestStringCut(t *testing.T) { 426 tests := []struct { 427 name string 428 input g.String 429 start g.String 430 end g.String 431 output g.String 432 }{ 433 {"Basic", "Hello [start]world[end]!", "[start]", "[end]", "world"}, 434 {"No start", "Hello world!", "[start]", "[end]", ""}, 435 {"No end", "Hello [start]world!", "[start]", "[end]", ""}, 436 {"Start equals end", "Hello [tag]world[tag]!", "[tag]", "[tag]", "world"}, 437 { 438 "Multiple instances", 439 "A [start]first[end] B [start]second[end] C", 440 "[start]", 441 "[end]", 442 "first", 443 }, 444 {"Empty input", "", "[start]", "[end]", ""}, 445 {"Empty start and end", "Hello world!", "", "", ""}, 446 { 447 "Nested tags", 448 "A [start]first [start]nested[end] value[end] B", 449 "[start]", 450 "[end]", 451 "first [start]nested", 452 }, 453 { 454 "Overlapping tags", 455 "A [start]first[end][start]second[end] B", 456 "[start]", 457 "[end]", 458 "first", 459 }, 460 {"Unicode characters", "Привет [начало]мир[конец]!", "[начало]", "[конец]", "мир"}, 461 } 462 463 for _, test := range tests { 464 t.Run(test.name, func(t *testing.T) { 465 _, result := test.input.Cut(test.start, test.end) 466 if result != test.output { 467 t.Errorf("Expected '%s', got '%s'", test.output, result) 468 } 469 }) 470 } 471 } 472 473 func TestStringCompare(t *testing.T) { 474 testCases := []struct { 475 str1 g.String 476 str2 g.String 477 expected int 478 }{ 479 {"apple", "banana", -1}, 480 {"banana", "apple", 1}, 481 {"banana", "banana", 0}, 482 {"apple", "Apple", 1}, 483 {"", "", 0}, 484 } 485 486 for _, tc := range testCases { 487 result := tc.str1.Cmp(tc.str2) 488 if int(result) != tc.expected { 489 t.Errorf("Compare(%q, %q): expected %d, got %d", tc.str1, tc.str2, tc.expected, result) 490 } 491 } 492 } 493 494 func TestStringEq(t *testing.T) { 495 testCases := []struct { 496 str1 g.String 497 str2 g.String 498 expected bool 499 }{ 500 {"apple", "banana", false}, 501 {"banana", "banana", true}, 502 {"Apple", "apple", false}, 503 {"", "", true}, 504 } 505 506 for _, tc := range testCases { 507 result := tc.str1.Eq(tc.str2) 508 if result != tc.expected { 509 t.Errorf("Eq(%q, %q): expected %t, got %t", tc.str1, tc.str2, tc.expected, result) 510 } 511 } 512 } 513 514 func TestStringNe(t *testing.T) { 515 testCases := []struct { 516 str1 g.String 517 str2 g.String 518 expected bool 519 }{ 520 {"apple", "banana", true}, 521 {"banana", "banana", false}, 522 {"Apple", "apple", true}, 523 {"", "", false}, 524 } 525 526 for _, tc := range testCases { 527 result := tc.str1.Ne(tc.str2) 528 if result != tc.expected { 529 t.Errorf("Ne(%q, %q): expected %t, got %t", tc.str1, tc.str2, tc.expected, result) 530 } 531 } 532 } 533 534 func TestStringGt(t *testing.T) { 535 testCases := []struct { 536 str1 g.String 537 str2 g.String 538 expected bool 539 }{ 540 {"apple", "banana", false}, 541 {"banana", "apple", true}, 542 {"Apple", "apple", false}, 543 {"banana", "banana", false}, 544 {"", "", false}, 545 } 546 547 for _, tc := range testCases { 548 result := tc.str1.Gt(tc.str2) 549 if result != tc.expected { 550 t.Errorf("Gt(%q, %q): expected %t, got %t", tc.str1, tc.str2, tc.expected, result) 551 } 552 } 553 } 554 555 func TestStringLt(t *testing.T) { 556 testCases := []struct { 557 str1 g.String 558 str2 g.String 559 expected bool 560 }{ 561 {"apple", "banana", true}, 562 {"banana", "apple", false}, 563 {"Apple", "apple", true}, 564 {"banana", "banana", false}, 565 {"", "", false}, 566 } 567 568 for _, tc := range testCases { 569 result := tc.str1.Lt(tc.str2) 570 if result != tc.expected { 571 t.Errorf("Lt(%q, %q): expected %t, got %t", tc.str1, tc.str2, tc.expected, result) 572 } 573 } 574 } 575 576 func TestStringLte(t *testing.T) { 577 testCases := []struct { 578 str1 g.String 579 str2 g.String 580 expected bool 581 }{ 582 {"apple", "banana", true}, 583 {"banana", "apple", false}, 584 {"Apple", "apple", true}, 585 {"banana", "banana", true}, // Equal strings should return true 586 {"", "", true}, // Empty strings should return true 587 } 588 589 for _, tc := range testCases { 590 result := tc.str1.Lte(tc.str2) 591 if result != tc.expected { 592 t.Errorf("Lte(%q, %q): expected %t, got %t", tc.str1, tc.str2, tc.expected, result) 593 } 594 } 595 } 596 597 func TestStringGte(t *testing.T) { 598 testCases := []struct { 599 str1 g.String 600 str2 g.String 601 expected bool 602 }{ 603 {"apple", "banana", false}, 604 {"banana", "apple", true}, 605 {"Apple", "apple", false}, 606 {"banana", "banana", true}, // Equal strings should return true 607 {"", "", true}, // Empty strings should return true 608 } 609 610 for _, tc := range testCases { 611 result := tc.str1.Gte(tc.str2) 612 if result != tc.expected { 613 t.Errorf("Gte(%q, %q): expected %t, got %t", tc.str1, tc.str2, tc.expected, result) 614 } 615 } 616 } 617 618 func TestStringReverse(t *testing.T) { 619 testCases := []struct { 620 in g.String 621 wantOut g.String 622 }{ 623 {in: "", wantOut: ""}, 624 {in: " ", wantOut: " "}, 625 {in: "a", wantOut: "a"}, 626 {in: "ab", wantOut: "ba"}, 627 {in: "abc", wantOut: "cba"}, 628 {in: "abcdefg", wantOut: "gfedcba"}, 629 {in: "ab丂d", wantOut: "d丂ba"}, 630 {in: "abåd", wantOut: "dåba"}, 631 632 {in: "世界", wantOut: "界世"}, 633 {in: "🙂🙃", wantOut: "🙃🙂"}, 634 {in: "こんにちは", wantOut: "はちにんこ"}, 635 636 // Punctuation and whitespace 637 {in: "Hello, world!", wantOut: "!dlrow ,olleH"}, 638 {in: "Hello\tworld!", wantOut: "!dlrow\tolleH"}, 639 {in: "Hello\nworld!", wantOut: "!dlrow\nolleH"}, 640 641 // Mixed languages and scripts 642 {in: "Hello, 世界!", wantOut: "!界世 ,olleH"}, 643 {in: "Привет, мир!", wantOut: "!рим ,тевирП"}, 644 {in: "안녕하세요, 세계!", wantOut: "!계세 ,요세하녕안"}, 645 646 // Palindromes 647 {in: "racecar", wantOut: "racecar"}, 648 {in: "A man, a plan, a canal: Panama", wantOut: "amanaP :lanac a ,nalp a ,nam A"}, 649 650 { 651 in: "The quick brown fox jumps over the lazy dog.", 652 wantOut: ".god yzal eht revo spmuj xof nworb kciuq ehT", 653 }, 654 {in: "A man a plan a canal panama", wantOut: "amanap lanac a nalp a nam A"}, 655 {in: "Was it a car or a cat I saw?", wantOut: "?was I tac a ro rac a ti saW"}, 656 {in: "Never odd or even", wantOut: "neve ro ddo reveN"}, 657 {in: "Do geese see God?", wantOut: "?doG ees eseeg oD"}, 658 {in: "A Santa at NASA", wantOut: "ASAN ta atnaS A"}, 659 {in: "Yo, Banana Boy!", wantOut: "!yoB ananaB ,oY"}, 660 {in: "Madam, in Eden I'm Adam", wantOut: "madA m'I nedE ni ,madaM"}, 661 {in: "Never odd or even", wantOut: "neve ro ddo reveN"}, 662 {in: "Was it a car or a cat I saw?", wantOut: "?was I tac a ro rac a ti saW"}, 663 {in: "Do geese see God?", wantOut: "?doG ees eseeg oD"}, 664 {in: "No 'x' in Nixon", wantOut: "noxiN ni 'x' oN"}, 665 {in: "A Santa at NASA", wantOut: "ASAN ta atnaS A"}, 666 {in: "Yo, Banana Boy!", wantOut: "!yoB ananaB ,oY"}, 667 } 668 669 for _, tc := range testCases { 670 result := tc.in.Reverse() 671 if result.Ne(tc.wantOut) { 672 t.Errorf("Reverse(%s): expected %s, got %s", tc.in, result, tc.wantOut) 673 } 674 } 675 } 676 677 func TestStringNormalizeNFC(t *testing.T) { 678 testCases := []struct { 679 input g.String 680 expected g.String 681 }{ 682 {input: "Mëtàl Hëàd", expected: "Mëtàl Hëàd"}, 683 {input: "Café", expected: "Café"}, 684 {input: "Ĵūņě", expected: "Ĵūņě"}, 685 {input: "𝓽𝓮𝓼𝓽 𝓬𝓪𝓼𝓮", expected: "𝓽𝓮𝓼𝓽 𝓬𝓪𝓼𝓮"}, 686 {input: "ḀϊṍẀṙṧ", expected: "ḀϊṍẀṙṧ"}, 687 {input: "えもじ れんしゅう", expected: "えもじ れんしゅう"}, 688 {input: "Научные исследования", expected: "Научные исследования"}, 689 {input: "🌟Unicode✨", expected: "🌟Unicode✨"}, 690 {input: "A\u0308", expected: "Ä"}, 691 {input: "o\u0308", expected: "ö"}, 692 {input: "u\u0308", expected: "ü"}, 693 {input: "O\u0308", expected: "Ö"}, 694 {input: "U\u0308", expected: "Ü"}, 695 } 696 697 for _, tc := range testCases { 698 t.Run("", func(t *testing.T) { 699 output := tc.input.NormalizeNFC() 700 if output != tc.expected { 701 t.Errorf("Normalize(%q) = %q; want %q", tc.input, output, tc.expected) 702 } 703 }) 704 } 705 } 706 707 func TestStringSimilarity(t *testing.T) { 708 testCases := []struct { 709 str1 g.String 710 str2 g.String 711 expected g.Float 712 }{ 713 {"hello", "hello", 100}, 714 {"hello", "world", 20}, 715 {"hello", "", 0}, 716 {"", "", 100}, 717 {"cat", "cats", 75}, 718 {"kitten", "sitting", 57.14}, 719 {"good", "bad", 25}, 720 {"book", "back", 50}, 721 {"abcdef", "azced", 50}, 722 {"tree", "three", 80}, 723 {"house", "horse", 80}, 724 {"language", "languish", 62.50}, 725 {"programming", "programmer", 72.73}, 726 {"algorithm", "logarithm", 77.78}, 727 {"software", "hardware", 50}, 728 {"tea", "ate", 33.33}, 729 {"pencil", "pen", 50}, 730 {"information", "informant", 63.64}, 731 {"coffee", "toffee", 83.33}, 732 {"developer", "develop", 77.78}, 733 {"distance", "difference", 50}, 734 {"similar", "similarity", 70}, 735 {"apple", "apples", 83.33}, 736 {"internet", "internets", 88.89}, 737 {"education", "dedication", 80}, 738 } 739 740 for _, tc := range testCases { 741 t.Run("", func(t *testing.T) { 742 output := tc.str1.Similarity(tc.str2) 743 if output.RoundDecimal(2).Ne(tc.expected) { 744 t.Errorf( 745 "g.String(\"%s\").SimilarText(\"%s\") = %.2f%% but want %.2f%%\n", 746 tc.str1, 747 tc.str2, 748 output, 749 tc.expected, 750 ) 751 } 752 }) 753 } 754 } 755 756 func TestStringReader(t *testing.T) { 757 tests := []struct { 758 name string 759 str g.String 760 expected string 761 }{ 762 {"Empty String", "", ""}, 763 {"Single character String", "a", "a"}, 764 {"Multiple characters String", "hello world", "hello world"}, 765 {"String with special characters", "こんにちは、世界!", "こんにちは、世界!"}, 766 } 767 768 for _, test := range tests { 769 t.Run(test.name, func(t *testing.T) { 770 reader := test.str.Reader() 771 resultBytes, err := io.ReadAll(reader) 772 if err != nil { 773 t.Fatalf("Error reading from *strings.Reader: %v", err) 774 } 775 776 result := string(resultBytes) 777 778 if result != test.expected { 779 t.Errorf("Reader() content = %s, expected %s", result, test.expected) 780 } 781 }) 782 } 783 } 784 785 func TestStringContainsAny(t *testing.T) { 786 testCases := []struct { 787 name string 788 input g.String 789 substrs g.Slice[g.String] 790 want bool 791 }{ 792 { 793 name: "ContainsAny_OneSubstringMatch", 794 input: "This is an example", 795 substrs: []g.String{"This", "missing"}, 796 want: true, 797 }, 798 { 799 name: "ContainsAny_NoSubstringMatch", 800 input: "This is an example", 801 substrs: []g.String{"notfound", "missing"}, 802 want: false, 803 }, 804 { 805 name: "ContainsAny_EmptySubstrings", 806 input: "This is an example", 807 substrs: []g.String{}, 808 want: false, 809 }, 810 { 811 name: "ContainsAny_EmptyInput", 812 input: "", 813 substrs: []g.String{"notfound", "missing"}, 814 want: false, 815 }, 816 } 817 818 for _, tc := range testCases { 819 t.Run(tc.name, func(t *testing.T) { 820 got := tc.input.ContainsAny(tc.substrs...) 821 if got != tc.want { 822 t.Errorf("ContainsAny() = %v; want %v", got, tc.want) 823 } 824 }) 825 } 826 } 827 828 func TestStringContainsAll(t *testing.T) { 829 testCases := []struct { 830 name string 831 input g.String 832 substrs g.Slice[g.String] 833 want bool 834 }{ 835 { 836 name: "ContainsAll_AllSubstringsMatch", 837 input: "This is an example", 838 substrs: []g.String{"This", "example"}, 839 want: true, 840 }, 841 { 842 name: "ContainsAll_NotAllSubstringsMatch", 843 input: "This is an example", 844 substrs: []g.String{"This", "missing"}, 845 want: false, 846 }, 847 { 848 name: "ContainsAll_EmptySubstrings", 849 input: "This is an example", 850 substrs: []g.String{}, 851 want: true, 852 }, 853 { 854 name: "ContainsAll_EmptyInput", 855 input: "", 856 substrs: []g.String{"notfound", "missing"}, 857 want: false, 858 }, 859 } 860 861 for _, tc := range testCases { 862 t.Run(tc.name, func(t *testing.T) { 863 got := tc.input.ContainsAll(tc.substrs...) 864 if got != tc.want { 865 t.Errorf("ContainsAll() = %v; want %v", got, tc.want) 866 } 867 }) 868 } 869 } 870 871 func TestStringReplaceNth(t *testing.T) { 872 tests := []struct { 873 name string 874 str g.String 875 oldS g.String 876 newS g.String 877 n g.Int 878 expected g.String 879 }{ 880 { 881 "First occurrence", 882 "The quick brown dog jumped over the lazy dog.", 883 "dog", 884 "fox", 885 1, 886 "The quick brown fox jumped over the lazy dog.", 887 }, 888 { 889 "Second occurrence", 890 "The quick brown dog jumped over the lazy dog.", 891 "dog", 892 "fox", 893 2, 894 "The quick brown dog jumped over the lazy fox.", 895 }, 896 { 897 "Last occurrence", 898 "The quick brown dog jumped over the lazy dog.", 899 "dog", 900 "fox", 901 -1, 902 "The quick brown dog jumped over the lazy fox.", 903 }, 904 { 905 "Negative n (except -1)", 906 "The quick brown dog jumped over the lazy dog.", 907 "dog", 908 "fox", 909 -2, 910 "The quick brown dog jumped over the lazy dog.", 911 }, 912 { 913 "Zero n", 914 "The quick brown dog jumped over the lazy dog.", 915 "dog", 916 "fox", 917 0, 918 "The quick brown dog jumped over the lazy dog.", 919 }, 920 { 921 "Longer replacement", 922 "Hello, world!", 923 "world", 924 "beautiful world", 925 1, 926 "Hello, beautiful world!", 927 }, 928 { 929 "Shorter replacement", 930 "A wonderful day, isn't it?", 931 "wonderful", 932 "nice", 933 1, 934 "A nice day, isn't it?", 935 }, 936 { 937 "Replace entire string", 938 "Hello, world!", 939 "Hello, world!", 940 "Greetings, world!", 941 1, 942 "Greetings, world!", 943 }, 944 {"No replacement", "Hello, world!", "x", "y", 1, "Hello, world!"}, 945 {"Nonexistent substring", "Hello, world!", "foobar", "test", 1, "Hello, world!"}, 946 {"Replace empty string", "Hello, world!", "", "x", 1, "Hello, world!"}, 947 {"Multiple identical substrings", "banana", "na", "xy", 1, "baxyna"}, 948 {"Multiple identical substrings, last", "banana", "na", "xy", -1, "banaxy"}, 949 {"Replace with empty string", "Hello, world!", "world", "", 1, "Hello, !"}, 950 {"Empty input string", "", "world", "test", 1, ""}, 951 {"Empty input, empty oldS, empty newS", "", "", "", 1, ""}, 952 {"Replace multiple spaces", "Hello world!", " ", " ", 1, "Hello world!"}, 953 {"Unicode characters", "こんにちは世界!", "世界", "World", 1, "こんにちはWorld!"}, 954 } 955 956 for _, test := range tests { 957 t.Run(test.name, func(t *testing.T) { 958 result := test.str.ReplaceNth(test.oldS, test.newS, test.n) 959 if result != test.expected { 960 t.Errorf("ReplaceNth() got %q, want %q", result, test.expected) 961 } 962 }) 963 } 964 } 965 966 func TestStringIsASCII(t *testing.T) { 967 testCases := []struct { 968 input g.String 969 expected bool 970 }{ 971 {"Hello, world!", true}, 972 {"こんにちは", false}, 973 {"", true}, 974 {"1234567890", true}, 975 {"ABCabc", true}, 976 {"~`!@#$%^&*()-_+={[}]|\\:;\"'<,>.?/", true}, 977 {"áéíóú", false}, 978 {"Привет", false}, 979 } 980 981 for _, tc := range testCases { 982 result := tc.input.IsASCII() 983 if result != tc.expected { 984 t.Errorf("IsASCII(%q) returned %v, expected %v", tc.input, result, tc.expected) 985 } 986 } 987 } 988 989 func TestStringReplaceMulti(t *testing.T) { 990 // Test case 1: Basic replacements 991 input1 := g.String("Hello, world! This is a test.") 992 replaced1 := input1.ReplaceMulti("Hello", "Greetings", "world", "universe", "test", "example") 993 expected1 := g.String("Greetings, universe! This is a example.") 994 if replaced1 != expected1 { 995 t.Errorf("Test case 1 failed: Expected '%s', got '%s'", expected1, replaced1) 996 } 997 998 // Test case 2: Replacements with special characters 999 input2 := g.String("The price is $100.00, not $200.00!") 1000 replaced2 := input2.ReplaceMulti("$100.00", "$50.00", "$200.00", "$80.00") 1001 expected2 := g.String("The price is $50.00, not $80.00!") 1002 if replaced2 != expected2 { 1003 t.Errorf("Test case 2 failed: Expected '%s', got '%s'", expected2, replaced2) 1004 } 1005 1006 // Test case 3: No replacements 1007 input3 := g.String("No replacements here.") 1008 replaced3 := input3.ReplaceMulti("Hello", "Greetings", "world", "universe") 1009 if replaced3 != input3 { 1010 t.Errorf("Test case 3 failed: Expected '%s', got '%s'", input3, replaced3) 1011 } 1012 1013 // Test case 4: Empty string 1014 input4 := g.String("") 1015 replaced4 := input4.ReplaceMulti("Hello", "Greetings") 1016 if replaced4 != input4 { 1017 t.Errorf("Test case 4 failed: Expected '%s', got '%s'", input4, replaced4) 1018 } 1019 } 1020 1021 func TestStringToFloat(t *testing.T) { 1022 // Test cases for valid float strings 1023 validFloatCases := []struct { 1024 input g.String 1025 expected g.Float 1026 }{ 1027 {"3.14", g.Float(3.14)}, 1028 {"-123.456", g.Float(-123.456)}, 1029 {"0.0", g.Float(0.0)}, 1030 } 1031 1032 for _, testCase := range validFloatCases { 1033 result := testCase.input.ToFloat() 1034 if result.IsErr() { 1035 t.Errorf("ToFloat test failed for %s. Unexpected error: %v", testCase.input, result.Err()) 1036 } 1037 1038 if result.Ok().Ne(testCase.expected) { 1039 t.Errorf("ToFloat test failed for %s. Expected: %v, Got: %v", 1040 testCase.input, 1041 testCase.expected, 1042 result.Ok(), 1043 ) 1044 } 1045 } 1046 1047 // Test cases for invalid float strings 1048 invalidFloatCases := []g.String{"abc", "123abc", "12.34.56", "", " "} 1049 1050 for _, input := range invalidFloatCases { 1051 result := input.ToFloat() 1052 if result.IsOk() { 1053 t.Errorf("ToFloat test failed for %s. Expected error, got result: %v", input, result.Ok()) 1054 } 1055 } 1056 } 1057 1058 func TestStringLower(t *testing.T) { 1059 // Test cases for lowercase conversion 1060 lowerCases := []struct { 1061 input g.String 1062 expected g.String 1063 }{ 1064 {"HELLO", "hello"}, 1065 {"Hello World", "hello world"}, 1066 {"123", "123"}, 1067 {"", ""}, 1068 {"AbCdEfG", "abcdefg"}, 1069 } 1070 1071 for _, testCase := range lowerCases { 1072 result := testCase.input.Lower() 1073 if !result.Eq(testCase.expected) { 1074 t.Errorf("Lower test failed for %s. Expected: %s, Got: %s", testCase.input, testCase.expected, result) 1075 } 1076 } 1077 } 1078 1079 func TestStringTrim(t *testing.T) { 1080 // Test cases for Trim 1081 trimCases := []struct { 1082 input g.String 1083 cutset g.String 1084 expected g.String 1085 }{ 1086 {" Hello, World! ", " ", "Hello, World!"}, 1087 {"Hello, World!", ",! ", "Hello, World"}, 1088 {" Golang ", " Go", "lang"}, 1089 {"", "", ""}, 1090 } 1091 1092 for _, testCase := range trimCases { 1093 result := testCase.input.Trim(testCase.cutset) 1094 if !result.Eq(testCase.expected) { 1095 t.Errorf( 1096 "Trim test failed for %s with cutset %s. Expected: %s, Got: %s", 1097 testCase.input, 1098 testCase.cutset, 1099 testCase.expected, 1100 result, 1101 ) 1102 } 1103 } 1104 } 1105 1106 func TestStringTrimLeft(t *testing.T) { 1107 // Test cases for TrimLeft 1108 trimLeftCases := []struct { 1109 input g.String 1110 cutset g.String 1111 expected g.String 1112 }{ 1113 {" Hello, World! ", " ", "Hello, World! "}, 1114 {"Hello, World!", ",! ", "Hello, World!"}, 1115 {" Golang ", " Go", "lang "}, 1116 {"", "", ""}, 1117 } 1118 1119 for _, testCase := range trimLeftCases { 1120 result := testCase.input.TrimLeft(testCase.cutset) 1121 if !result.Eq(testCase.expected) { 1122 t.Errorf( 1123 "TrimLeft test failed for %s with cutset %s. Expected: %s, Got: %s", 1124 testCase.input, 1125 testCase.cutset, 1126 testCase.expected, 1127 result, 1128 ) 1129 } 1130 } 1131 } 1132 1133 func TestStringTrimPrefix(t *testing.T) { 1134 // Test cases for TrimPrefix 1135 trimPrefixCases := []struct { 1136 input g.String 1137 prefix g.String 1138 expected g.String 1139 }{ 1140 {"Hello, World!", "Hello, ", "World!"}, 1141 {"prefix-prefix-suffix", "prefix-", "prefix-suffix"}, 1142 {"no prefix", "prefix-", "no prefix"}, 1143 {"", "prefix-", ""}, 1144 } 1145 1146 for _, testCase := range trimPrefixCases { 1147 result := testCase.input.TrimPrefix(testCase.prefix) 1148 if !result.Eq(testCase.expected) { 1149 t.Errorf( 1150 "TrimPrefix test failed for %s with prefix %s. Expected: %s, Got: %s", 1151 testCase.input, 1152 testCase.prefix, 1153 testCase.expected, 1154 result, 1155 ) 1156 } 1157 } 1158 } 1159 1160 func TestStringTrimSuffix(t *testing.T) { 1161 // Test cases for TrimSuffix 1162 trimSuffixCases := []struct { 1163 input g.String 1164 suffix g.String 1165 expected g.String 1166 }{ 1167 {"Hello, World!", ", World!", "Hello"}, 1168 {"prefix-prefix-suffix", "-suffix", "prefix-prefix"}, 1169 {"no suffix", "-suffix", "no suffix"}, 1170 {"", "-suffix", ""}, 1171 } 1172 1173 for _, testCase := range trimSuffixCases { 1174 result := testCase.input.TrimSuffix(testCase.suffix) 1175 if !result.Eq(testCase.expected) { 1176 t.Errorf( 1177 "TrimSuffix test failed for %s with suffix %s. Expected: %s, Got: %s", 1178 testCase.input, 1179 testCase.suffix, 1180 testCase.expected, 1181 result, 1182 ) 1183 } 1184 } 1185 } 1186 1187 func TestStringReplace(t *testing.T) { 1188 // Test cases for Replace 1189 replaceCases := []struct { 1190 input g.String 1191 oldS g.String 1192 newS g.String 1193 n g.Int 1194 expected g.String 1195 }{ 1196 {"Hello, World!", "Hello", "Hi", 1, "Hi, World!"}, 1197 {"Hello, Hello, Hello!", "Hello", "Hi", -1, "Hi, Hi, Hi!"}, 1198 {"prefix-prefix-suffix", "prefix", "pre", 1, "pre-prefix-suffix"}, 1199 {"no match", "match", "replacement", 1, "no replacement"}, 1200 {"", "", "", 0, ""}, 1201 } 1202 1203 for _, testCase := range replaceCases { 1204 result := testCase.input.Replace(testCase.oldS, testCase.newS, testCase.n) 1205 if !result.Eq(testCase.expected) { 1206 t.Errorf( 1207 "Replace test failed for %s with oldS %s and newS %s. Expected: %s, Got: %s", 1208 testCase.input, 1209 testCase.oldS, 1210 testCase.newS, 1211 testCase.expected, 1212 result, 1213 ) 1214 } 1215 } 1216 } 1217 1218 func TestStringContainsAnyChars(t *testing.T) { 1219 // Test cases for ContainsAnyChars 1220 containsAnyCharsCases := []struct { 1221 input g.String 1222 chars g.String 1223 expected bool 1224 }{ 1225 {"Hello, World!", "aeiou", true}, // Contains vowels 1226 {"1234567890", "aeiou", false}, // Does not contain vowels 1227 {"Hello, World!", "abc", false}, // Contains a, b, or c 1228 {"Hello, World!", "123", false}, // Does not contain 1, 2, or 3 1229 {"", "aeiou", false}, // Empty string 1230 } 1231 1232 for _, testCase := range containsAnyCharsCases { 1233 result := testCase.input.ContainsAnyChars(testCase.chars) 1234 if result != testCase.expected { 1235 t.Errorf( 1236 "ContainsAnyChars test failed for %s with chars %s. Expected: %t, Got: %t", 1237 testCase.input, 1238 testCase.chars, 1239 testCase.expected, 1240 result, 1241 ) 1242 } 1243 } 1244 } 1245 1246 func TestStringSplitLines(t *testing.T) { 1247 // Test case 1: String with multiple lines. 1248 str1 := g.NewString("hello\nworld\nhow\nare\nyou\n") 1249 expected1 := g.Slice[g.String]{"hello", "world", "how", "are", "you"} 1250 result1 := str1.Lines().Collect() 1251 if !reflect.DeepEqual(result1, expected1) { 1252 t.Errorf("Test case 1 failed: Expected %v, got %v", expected1, result1) 1253 } 1254 1255 // Test case 2: String with single line. 1256 str2 := g.NewString("hello") 1257 expected2 := g.Slice[g.String]{"hello"} 1258 result2 := str2.Lines().Collect() 1259 if !reflect.DeepEqual(result2, expected2) { 1260 t.Errorf("Test case 2 failed: Expected %v, got %v", expected2, result2) 1261 } 1262 } 1263 1264 func TestStringSplitN(t *testing.T) { 1265 // Test case 1: String with multiple segments, n > 0. 1266 str1 := g.NewString("hello,world,how,are,you") 1267 sep1 := g.NewString(",") 1268 n1 := g.Int(3) 1269 expected1 := g.Slice[g.String]{"hello", "world", "how,are,you"} 1270 result1 := str1.SplitN(sep1, n1) 1271 if !reflect.DeepEqual(result1, expected1) { 1272 t.Errorf("Test case 1 failed: Expected %v, got %v", expected1, result1) 1273 } 1274 1275 // Test case 2: String with multiple segments, n < 0. 1276 str2 := g.NewString("hello,world,how,are,you") 1277 sep2 := g.NewString(",") 1278 n2 := g.Int(-1) 1279 expected2 := g.Slice[g.String]{"hello", "world", "how", "are", "you"} 1280 result2 := str2.SplitN(sep2, n2) 1281 if !reflect.DeepEqual(result2, expected2) { 1282 t.Errorf("Test case 2 failed: Expected %v, got %v", expected2, result2) 1283 } 1284 1285 // Test case 3: String with single segment, n > 0. 1286 str3 := g.NewString("hello") 1287 sep3 := g.NewString(",") 1288 n3 := g.Int(1) 1289 expected3 := g.Slice[g.String]{"hello"} 1290 result3 := str3.SplitN(sep3, n3) 1291 if !reflect.DeepEqual(result3, expected3) { 1292 t.Errorf("Test case 3 failed: Expected %v, got %v", expected3, result3) 1293 } 1294 } 1295 1296 func TestStringFields(t *testing.T) { 1297 // Test case 1: String with multiple words separated by whitespace. 1298 str1 := g.NewString("hello world how are you") 1299 expected1 := g.Slice[g.String]{"hello", "world", "how", "are", "you"} 1300 result1 := str1.Fields().Collect() 1301 if !reflect.DeepEqual(result1, expected1) { 1302 t.Errorf("Test case 1 failed: Expected %v, got %v", expected1, result1) 1303 } 1304 1305 // Test case 2: String with single word. 1306 str2 := g.NewString("hello") 1307 expected2 := g.Slice[g.String]{"hello"} 1308 result2 := str2.Fields().Collect() 1309 if !reflect.DeepEqual(result2, expected2) { 1310 t.Errorf("Test case 2 failed: Expected %v, got %v", expected2, result2) 1311 } 1312 1313 // Test case 3: Empty string. 1314 str3 := g.NewString("") 1315 expected3 := g.Slice[g.String]{} 1316 result3 := str3.Fields().Collect() 1317 if !reflect.DeepEqual(result3, expected3) { 1318 t.Errorf("Test case 3 failed: Expected %v, got %v", expected3, result3) 1319 } 1320 1321 // Test case 4: String with leading and trailing whitespace. 1322 str4 := g.NewString(" hello world ") 1323 expected4 := g.Slice[g.String]{"hello", "world"} 1324 result4 := str4.Fields().Collect() 1325 if !reflect.DeepEqual(result4, expected4) { 1326 t.Errorf("Test case 4 failed: Expected %v, got %v", expected4, result4) 1327 } 1328 } 1329 1330 func TestStringCount(t *testing.T) { 1331 // Test case 1: Count occurrences of substring in a string with multiple occurrences. 1332 str1 := g.NewString("hello world hello hello") 1333 substr1 := g.NewString("hello") 1334 expected1 := g.Int(3) 1335 result1 := str1.Count(substr1) 1336 if result1 != expected1 { 1337 t.Errorf("Test case 1 failed: Expected %d, got %d", expected1, result1) 1338 } 1339 1340 // Test case 2: Count occurrences of substring in a string with no occurrences. 1341 str2 := g.NewString("abcdefg") 1342 substr2 := g.NewString("xyz") 1343 expected2 := g.Int(0) 1344 result2 := str2.Count(substr2) 1345 if result2 != expected2 { 1346 t.Errorf("Test case 2 failed: Expected %d, got %d", expected2, result2) 1347 } 1348 1349 // Test case 3: Count occurrences of substring in an empty string. 1350 str3 := g.NewString("") 1351 substr3 := g.NewString("hello") 1352 expected3 := g.Int(0) 1353 result3 := str3.Count(substr3) 1354 if result3 != expected3 { 1355 t.Errorf("Test case 3 failed: Expected %d, got %d", expected3, result3) 1356 } 1357 } 1358 1359 func TestStringEqFold(t *testing.T) { 1360 // Test case 1: Strings are equal case-insensitively. 1361 str1 := g.NewString("Hello") 1362 str2 := g.NewString("hello") 1363 expected1 := true 1364 result1 := str1.EqFold(str2) 1365 if result1 != expected1 { 1366 t.Errorf("Test case 1 failed: Expected %t, got %t", expected1, result1) 1367 } 1368 1369 // Test case 2: Strings are not equal case-insensitively. 1370 str3 := g.NewString("world") 1371 expected2 := false 1372 result2 := str1.EqFold(str3) 1373 if result2 != expected2 { 1374 t.Errorf("Test case 2 failed: Expected %t, got %t", expected2, result2) 1375 } 1376 1377 // Test case 3: Empty strings. 1378 str4 := g.NewString("") 1379 str5 := g.NewString("") 1380 expected3 := true 1381 result3 := str4.EqFold(str5) 1382 if result3 != expected3 { 1383 t.Errorf("Test case 3 failed: Expected %t, got %t", expected3, result3) 1384 } 1385 } 1386 1387 func TestStringLastIndex(t *testing.T) { 1388 // Test case 1: Substring is present in the string. 1389 str1 := g.NewString("hello world hello") 1390 substr1 := g.NewString("hello") 1391 expected1 := g.Int(12) 1392 result1 := str1.LastIndex(substr1) 1393 if result1 != expected1 { 1394 t.Errorf("Test case 1 failed: Expected %d, got %d", expected1, result1) 1395 } 1396 1397 // Test case 2: Substring is not present in the string. 1398 substr2 := g.NewString("foo") 1399 expected2 := g.Int(-1) 1400 result2 := str1.LastIndex(substr2) 1401 if result2 != expected2 { 1402 t.Errorf("Test case 2 failed: Expected %d, got %d", expected2, result2) 1403 } 1404 1405 // Test case 3: Empty string. 1406 str3 := g.NewString("") 1407 substr3 := g.NewString("hello") 1408 expected3 := g.Int(-1) 1409 result3 := str3.LastIndex(substr3) 1410 if result3 != expected3 { 1411 t.Errorf("Test case 3 failed: Expected %d, got %d", expected3, result3) 1412 } 1413 } 1414 1415 func TestStringIndexRune(t *testing.T) { 1416 // Test case 1: Rune is present in the string. 1417 str1 := g.NewString("hello") 1418 rune1 := 'e' 1419 expected1 := g.Int(1) 1420 result1 := str1.IndexRune(rune1) 1421 if result1 != expected1 { 1422 t.Errorf("Test case 1 failed: Expected %d, got %d", expected1, result1) 1423 } 1424 1425 // Test case 2: Rune is not present in the string. 1426 rune2 := 'x' 1427 expected2 := g.Int(-1) 1428 result2 := str1.IndexRune(rune2) 1429 if result2 != expected2 { 1430 t.Errorf("Test case 2 failed: Expected %d, got %d", expected2, result2) 1431 } 1432 1433 // Test case 3: Empty string. 1434 str3 := g.NewString("") 1435 rune3 := 'h' 1436 expected3 := g.Int(-1) 1437 result3 := str3.IndexRune(rune3) 1438 if result3 != expected3 { 1439 t.Errorf("Test case 3 failed: Expected %d, got %d", expected3, result3) 1440 } 1441 } 1442 1443 func TestStringNotEmpty(t *testing.T) { 1444 // Test case 1: String is not empty. 1445 str1 := g.NewString("hello") 1446 expected1 := true 1447 result1 := str1.NotEmpty() 1448 if result1 != expected1 { 1449 t.Errorf("Test case 1 failed: Expected %t, got %t", expected1, result1) 1450 } 1451 1452 // Test case 2: String is empty. 1453 str2 := g.NewString("") 1454 expected2 := false 1455 result2 := str2.NotEmpty() 1456 if result2 != expected2 { 1457 t.Errorf("Test case 2 failed: Expected %t, got %t", expected2, result2) 1458 } 1459 } 1460 1461 func TestRepeat(t *testing.T) { 1462 // Test case 1: Repeat count is positive. 1463 str := g.NewString("abc") 1464 count := g.Int(3) 1465 expected1 := g.NewString("abcabcabc") 1466 result1 := str.Repeat(count) 1467 if !result1.Eq(expected1) { 1468 t.Errorf("Test case 1 failed: Expected %s, got %s", expected1, result1) 1469 } 1470 1471 // Test case 2: Repeat count is zero. 1472 count = 0 1473 expected2 := g.NewString("") 1474 result2 := str.Repeat(count) 1475 if !result2.Eq(expected2) { 1476 t.Errorf("Test case 2 failed: Expected %s, got %s", expected2, result2) 1477 } 1478 } 1479 1480 func TestStringLeftJustify(t *testing.T) { 1481 // Test case 1: Original string length is less than the specified length. 1482 str1 := g.NewString("Hello") 1483 length1 := g.Int(10) 1484 pad1 := g.NewString(".") 1485 expected1 := g.NewString("Hello.....") 1486 result1 := str1.LeftJustify(length1, pad1) 1487 if !result1.Eq(expected1) { 1488 t.Errorf("Test case 1 failed: Expected %s, got %s", expected1, result1) 1489 } 1490 1491 // Test case 2: Original string length is equal to the specified length. 1492 str2 := g.NewString("Hello") 1493 length2 := g.Int(5) 1494 pad2 := g.NewString(".") 1495 expected2 := g.NewString("Hello") 1496 result2 := str2.LeftJustify(length2, pad2) 1497 if !result2.Eq(expected2) { 1498 t.Errorf("Test case 2 failed: Expected %s, got %s", expected2, result2) 1499 } 1500 1501 // Test case 3: Original string length is greater than the specified length. 1502 str3 := g.NewString("Hello") 1503 length3 := g.Int(3) 1504 pad3 := g.NewString(".") 1505 expected3 := g.NewString("Hello") 1506 result3 := str3.LeftJustify(length3, pad3) 1507 if !result3.Eq(expected3) { 1508 t.Errorf("Test case 3 failed: Expected %s, got %s", expected3, result3) 1509 } 1510 1511 // Test case 4: Empty padding string. 1512 str4 := g.NewString("Hello") 1513 length4 := g.Int(10) 1514 pad4 := g.NewString("") 1515 expected4 := g.NewString("Hello") 1516 result4 := str4.LeftJustify(length4, pad4) 1517 if !result4.Eq(expected4) { 1518 t.Errorf("Test case 4 failed: Expected %s, got %s", expected4, result4) 1519 } 1520 } 1521 1522 func TestStringRightJustify(t *testing.T) { 1523 // Test case 1: Original string length is less than the specified length. 1524 str1 := g.NewString("Hello") 1525 length1 := g.Int(10) 1526 pad1 := g.NewString(".") 1527 expected1 := g.NewString(".....Hello") 1528 result1 := str1.RightJustify(length1, pad1) 1529 if !result1.Eq(expected1) { 1530 t.Errorf("Test case 1 failed: Expected %s, got %s", expected1, result1) 1531 } 1532 1533 // Test case 2: Original string length is equal to the specified length. 1534 str2 := g.NewString("Hello") 1535 length2 := g.Int(5) 1536 pad2 := g.NewString(".") 1537 expected2 := g.NewString("Hello") 1538 result2 := str2.RightJustify(length2, pad2) 1539 if !result2.Eq(expected2) { 1540 t.Errorf("Test case 2 failed: Expected %s, got %s", expected2, result2) 1541 } 1542 1543 // Test case 3: Original string length is greater than the specified length. 1544 str3 := g.NewString("Hello") 1545 length3 := g.Int(3) 1546 pad3 := g.NewString(".") 1547 expected3 := g.NewString("Hello") 1548 result3 := str3.RightJustify(length3, pad3) 1549 if !result3.Eq(expected3) { 1550 t.Errorf("Test case 3 failed: Expected %s, got %s", expected3, result3) 1551 } 1552 1553 // Test case 4: Empty padding string. 1554 str4 := g.NewString("Hello") 1555 length4 := g.Int(10) 1556 pad4 := g.NewString("") 1557 expected4 := g.NewString("Hello") 1558 result4 := str4.RightJustify(length4, pad4) 1559 if !result4.Eq(expected4) { 1560 t.Errorf("Test case 4 failed: Expected %s, got %s", expected4, result4) 1561 } 1562 } 1563 1564 func TestStringCenter(t *testing.T) { 1565 // Test case 1: Original string length is less than the specified length. 1566 str1 := g.NewString("Hello") 1567 length1 := g.Int(10) 1568 pad1 := g.NewString(".") 1569 expected1 := g.NewString("..Hello...") 1570 result1 := str1.Center(length1, pad1) 1571 if !result1.Eq(expected1) { 1572 t.Errorf("Test case 1 failed: Expected %s, got %s", expected1, result1) 1573 } 1574 1575 // Test case 2: Original string length is equal to the specified length. 1576 str2 := g.NewString("Hello") 1577 length2 := g.Int(5) 1578 pad2 := g.NewString(".") 1579 expected2 := g.NewString("Hello") 1580 result2 := str2.Center(length2, pad2) 1581 if !result2.Eq(expected2) { 1582 t.Errorf("Test case 2 failed: Expected %s, got %s", expected2, result2) 1583 } 1584 1585 // Test case 3: Original string length is greater than the specified length. 1586 str3 := g.NewString("Hello") 1587 length3 := g.Int(3) 1588 pad3 := g.NewString(".") 1589 expected3 := g.NewString("Hello") 1590 result3 := str3.Center(length3, pad3) 1591 if !result3.Eq(expected3) { 1592 t.Errorf("Test case 3 failed: Expected %s, got %s", expected3, result3) 1593 } 1594 1595 // Test case 4: Empty padding string. 1596 str4 := g.NewString("Hello") 1597 length4 := g.Int(10) 1598 pad4 := g.NewString("") 1599 expected4 := g.NewString("Hello") 1600 result4 := str4.Center(length4, pad4) 1601 if !result4.Eq(expected4) { 1602 t.Errorf("Test case 4 failed: Expected %s, got %s", expected4, result4) 1603 } 1604 } 1605 1606 func TestStringEndsWith(t *testing.T) { 1607 // Test case 1: String ends with one of the provided suffixes. 1608 str1 := g.NewString("example.com") 1609 suffixes1 := g.Slice[g.String]{g.NewString(".com"), g.NewString(".net")} 1610 expected1 := true 1611 result1 := str1.EndsWith(suffixes1...) 1612 if result1 != expected1 { 1613 t.Errorf("Test case 1 failed: Expected %t, got %t", expected1, result1) 1614 } 1615 1616 // Test case 2: String ends with multiple provided suffixes. 1617 str2 := g.NewString("example.net") 1618 suffixes2 := g.Slice[g.String]{g.NewString(".com"), g.NewString(".net")} 1619 expected2 := true 1620 result2 := str2.EndsWith(suffixes2...) 1621 if result2 != expected2 { 1622 t.Errorf("Test case 2 failed: Expected %t, got %t", expected2, result2) 1623 } 1624 1625 // Test case 3: String does not end with any of the provided suffixes. 1626 str3 := g.NewString("example.org") 1627 suffixes3 := g.Slice[g.String]{g.NewString(".com"), g.NewString(".net")} 1628 expected3 := false 1629 result3 := str3.EndsWith(suffixes3...) 1630 if result3 != expected3 { 1631 t.Errorf("Test case 3 failed: Expected %t, got %t", expected3, result3) 1632 } 1633 } 1634 1635 func TestStringStartsWith(t *testing.T) { 1636 // Test cases 1637 testCases := []struct { 1638 str g.String 1639 prefixes []g.String 1640 expected bool 1641 }{ 1642 {"http://example.com", []g.String{"http://", "https://"}, true}, 1643 {"https://example.com", []g.String{"http://", "https://"}, true}, 1644 {"ftp://example.com", []g.String{"http://", "https://"}, false}, 1645 {"", []g.String{""}, true}, // Empty string should match empty prefix 1646 {"", []g.String{"non-empty"}, false}, 1647 } 1648 1649 // Test each case 1650 for _, tc := range testCases { 1651 // Wrap the input string 1652 s := g.String(tc.str) 1653 1654 // Call the StartsWith method 1655 result := s.StartsWith(tc.prefixes...) 1656 1657 // Assert the result 1658 if result != tc.expected { 1659 t.Errorf("StartsWith() returned %v; expected %v", result, tc.expected) 1660 } 1661 } 1662 } 1663 1664 func TestStringSplitAfter(t *testing.T) { 1665 testCases := []struct { 1666 input g.String 1667 separator g.String 1668 expected g.Slice[g.String] 1669 }{ 1670 {"hello,world,how,are,you", ",", g.Slice[g.String]{"hello,", "world,", "how,", "are,", "you"}}, 1671 {"apple banana cherry", " ", g.Slice[g.String]{"apple ", "banana ", "cherry"}}, 1672 {"a-b-c-d-e", "-", g.Slice[g.String]{"a-", "b-", "c-", "d-", "e"}}, 1673 {"abcd", "a", g.Slice[g.String]{"a", "bcd"}}, 1674 {"thisistest", "is", g.Slice[g.String]{"this", "is", "test"}}, 1675 {"☺☻☹", "", g.Slice[g.String]{"☺", "☻", "☹"}}, 1676 {"☺☻☹", "☹", g.Slice[g.String]{"☺☻☹", ""}}, 1677 {"123", "", g.Slice[g.String]{"1", "2", "3"}}, 1678 } 1679 1680 for _, tc := range testCases { 1681 actual := tc.input.SplitAfter(tc.separator).Collect() 1682 1683 if !reflect.DeepEqual(actual, tc.expected) { 1684 t.Errorf( 1685 "Unexpected result for input: %s, separator: %s\nExpected: %v\nGot: %v", 1686 tc.input, 1687 tc.separator, 1688 tc.expected, 1689 actual, 1690 ) 1691 } 1692 } 1693 } 1694 1695 func TestStringFieldsBy(t *testing.T) { 1696 testCases := []struct { 1697 input g.String 1698 fn func(r rune) bool 1699 expected g.Slice[g.String] 1700 }{ 1701 {"hello world", unicode.IsSpace, g.Slice[g.String]{"hello", "world"}}, 1702 {"1,2,3,4,5", func(r rune) bool { return r == ',' }, g.Slice[g.String]{"1", "2", "3", "4", "5"}}, 1703 {"camelCcase", unicode.IsUpper, g.Slice[g.String]{"camel", "case"}}, 1704 } 1705 1706 for _, tc := range testCases { 1707 actual := tc.input.FieldsBy(tc.fn).Collect() 1708 1709 if !reflect.DeepEqual(actual, tc.expected) { 1710 t.Errorf("Unexpected result for input: %s\nExpected: %v\nGot: %v", tc.input, tc.expected, actual) 1711 } 1712 } 1713 } 1714 1715 func TestStringTrimSpace(t *testing.T) { 1716 testCases := []struct { 1717 input g.String 1718 expected g.String 1719 }{ 1720 {" hello ", "hello"}, 1721 {" world", "world"}, 1722 {"foo ", "foo"}, 1723 {"\tbar\t", "bar"}, 1724 {"", ""}, 1725 {" ", ""}, 1726 } 1727 1728 for _, tc := range testCases { 1729 actual := tc.input.TrimSpace() 1730 1731 if actual != tc.expected { 1732 t.Errorf("Unexpected result for input: %s\nExpected: %s\nGot: %s", tc.input, tc.expected, actual) 1733 } 1734 } 1735 } 1736 1737 func TestStringRemove(t *testing.T) { 1738 tests := []struct { 1739 original g.String 1740 matches g.Slice[g.String] 1741 expected g.String 1742 }{ 1743 { 1744 original: "Hello, world! This is a test.", 1745 matches: g.Slice[g.String]{"Hello", "test"}, 1746 expected: ", world! This is a .", 1747 }, 1748 { 1749 original: "This is a test string. This is a test string.", 1750 matches: g.Slice[g.String]{"test", "string"}, 1751 expected: "This is a . This is a .", 1752 }, 1753 { 1754 original: "I love ice cream. Ice cream is delicious.", 1755 matches: g.Slice[g.String]{"Ice", "cream"}, 1756 expected: "I love ice . is delicious.", 1757 }, 1758 } 1759 1760 for _, test := range tests { 1761 original := test.original 1762 modified := original.Remove(test.matches...) 1763 if modified != test.expected { 1764 t.Errorf("Remove(%q, %q) = %q, expected %q", test.original, test.matches, modified.Std(), test.expected) 1765 } 1766 } 1767 }