Update utf8 task

This commit is contained in:
Fedor Korotkiy 2021-02-18 13:37:40 +03:00
parent f9f60e3656
commit 84d9f411c5
4 changed files with 43 additions and 1 deletions

View file

@ -5,9 +5,24 @@
Функция принимает на вход юникодную строку и должна возвращать строку, Функция принимает на вход юникодную строку и должна возвращать строку,
состоящую из тех же юникодных рун, но записанных в обратном порядке. состоящую из тех же юникодных рун, но записанных в обратном порядке.
Если строка содержит последовательность байт, не образующую корректный utf8, нужно развернуть
эту последовательность как отдельные байты.
Обратите внимание в тестах, что некоторые графемы распадаются при обращении строки. Обратите внимание в тестах, что некоторые графемы распадаются при обращении строки.
Данный эффект связан с тем, что в юникоде некоторые руны умеют комбинироваться в одну графему. Данный эффект связан с тем, что в юникоде некоторые руны умеют комбинироваться в одну графему.
Ваша реализация должна быть достаточно эффективна. На нашем бенчмарке в тестовой системе
она должна работать не хуже авторского решения. В частности, код должен делать не больше двух
аллокаций. Эту функцию можно написать с одной аллокацией, но придётся использовать пакет unsafe.
Работу с unsafe мы будем разбирать дальше в курсе.
```
goos: linux
goarch: amd64
pkg: gitlab.com/slon/shad-go/utf8/reverse
BenchmarkReverse-4 395078 2763 ns/op 1792 B/op 2 allocs/op
PASS
```
### Примеры ### Примеры
Как запустить все тесты: Как запустить все тесты:

View file

@ -2,6 +2,7 @@ package reverse
import ( import (
"fmt" "fmt"
"strings"
"testing" "testing"
"github.com/stretchr/testify/require" "github.com/stretchr/testify/require"
@ -36,9 +37,20 @@ func TestReverse(t *testing.T) {
{input: "🇩🇪", output: "🇪🇩"}, {input: "🇩🇪", output: "🇪🇩"},
// NB: Флаг распался. :) // NB: Флаг распался. :)
{input: "🏳️‍🌈", output: "🌈‍️🏳"}, {input: "🏳️‍🌈", output: "🌈‍️🏳"},
{input: "\xff\x00\xff\x00", output: "\x00\xff\x00\xff"},
} { } {
t.Run(fmt.Sprintf("#%v: %v", i, tc.input), func(t *testing.T) { t.Run(fmt.Sprintf("#%v: %v", i, tc.input), func(t *testing.T) {
require.Equal(t, tc.output, Reverse(tc.input)) require.Equal(t, tc.output, Reverse(tc.input))
}) })
} }
} }
func BenchmarkReverse(b *testing.B) {
input := strings.Repeat("🙂🙂", 100)
b.ReportAllocs()
for i := 0; i < b.N; i++ {
_ = Reverse(input)
}
}

View file

@ -5,9 +5,12 @@
Функция принимает на вход юникодную строку и должна возвращать строку, Функция принимает на вход юникодную строку и должна возвращать строку,
состоящую из тех же символов, но где все подряд идущие группы пробельных символов заменены на ' ' (один обычный пробел). состоящую из тех же символов, но где все подряд идущие группы пробельных символов заменены на ' ' (один обычный пробел).
### Примеры Некорректную utf8 последовательность функция должна оставлять без изменений.
## Примеры
Как запустить все тесты: Как запустить все тесты:
``` ```
go test -v ./utf8/spacecollapse/... go test -v ./utf8/spacecollapse/...
``` ```

View file

@ -2,6 +2,7 @@ package spacecollapse
import ( import (
"fmt" "fmt"
"strings"
"testing" "testing"
"github.com/stretchr/testify/require" "github.com/stretchr/testify/require"
@ -21,9 +22,20 @@ func TestCollapseSpaces(t *testing.T) {
{input: "\t*", output: " *"}, {input: "\t*", output: " *"},
{input: " \t \t ", output: " "}, {input: " \t \t ", output: " "},
{input: " \tx\t ", output: " x "}, {input: " \tx\t ", output: " x "},
{input: "\xff\x00\xff\x00", output: "\xff\x00\xff\x00"},
} { } {
t.Run(fmt.Sprintf("#%v: %v", i, tc.input), func(t *testing.T) { t.Run(fmt.Sprintf("#%v: %v", i, tc.input), func(t *testing.T) {
require.Equal(t, tc.output, CollapseSpaces(tc.input)) require.Equal(t, tc.output, CollapseSpaces(tc.input))
}) })
} }
} }
func BenchmarkCollapse(b *testing.B) {
input := strings.Repeat("🙂 🙂", 100)
b.ReportAllocs()
for i := 0; i < b.N; i++ {
_ = CollapseSpaces(input)
}
}