golang.org/x/text@v0.14.0/collate/tools/colcmp/col.go (about) 1 // Copyright 2012 The Go Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style 3 // license that can be found in the LICENSE file. 4 5 package main 6 7 import ( 8 "log" 9 "unicode/utf16" 10 11 "golang.org/x/text/collate" 12 "golang.org/x/text/language" 13 ) 14 15 // Input holds an input string in both UTF-8 and UTF-16 format. 16 type Input struct { 17 index int // used for restoring to original random order 18 UTF8 []byte 19 UTF16 []uint16 20 key []byte // used for sorting 21 } 22 23 func (i Input) String() string { 24 return string(i.UTF8) 25 } 26 27 func makeInput(s8 []byte, s16 []uint16) Input { 28 return Input{UTF8: s8, UTF16: s16} 29 } 30 31 func makeInputString(s string) Input { 32 return Input{ 33 UTF8: []byte(s), 34 UTF16: utf16.Encode([]rune(s)), 35 } 36 } 37 38 // Collator is an interface for architecture-specific implementations of collation. 39 type Collator interface { 40 // Key generates a sort key for the given input. Implemenations 41 // may return nil if a collator does not support sort keys. 42 Key(s Input) []byte 43 44 // Compare returns -1 if a < b, 1 if a > b and 0 if a == b. 45 Compare(a, b Input) int 46 } 47 48 // CollatorFactory creates a Collator for a given language tag. 49 type CollatorFactory struct { 50 name string 51 makeFn func(tag string) (Collator, error) 52 description string 53 } 54 55 var collators = []CollatorFactory{} 56 57 // AddFactory registers f as a factory for an implementation of Collator. 58 func AddFactory(f CollatorFactory) { 59 collators = append(collators, f) 60 } 61 62 func getCollator(name, locale string) Collator { 63 for _, f := range collators { 64 if f.name == name { 65 col, err := f.makeFn(locale) 66 if err != nil { 67 log.Fatal(err) 68 } 69 return col 70 } 71 } 72 log.Fatalf("collator of type %q not found", name) 73 return nil 74 } 75 76 // goCollator is an implementation of Collator using go's own collator. 77 type goCollator struct { 78 c *collate.Collator 79 buf collate.Buffer 80 } 81 82 func init() { 83 AddFactory(CollatorFactory{"go", newGoCollator, "Go's native collator implementation."}) 84 } 85 86 func newGoCollator(loc string) (Collator, error) { 87 c := &goCollator{c: collate.New(language.Make(loc))} 88 return c, nil 89 } 90 91 func (c *goCollator) Key(b Input) []byte { 92 return c.c.Key(&c.buf, b.UTF8) 93 } 94 95 func (c *goCollator) Compare(a, b Input) int { 96 return c.c.Compare(a.UTF8, b.UTF8) 97 }