barometer: update DMA's vendoring packages
[barometer.git] / src / dma / vendor / golang.org / x / text / internal / tag / tag.go
1 // Copyright 2015 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 tag contains functionality handling tags and related data.
6 package tag // import "golang.org/x/text/internal/tag"
7
8 import "sort"
9
10 // An Index converts tags to a compact numeric value.
11 //
12 // All elements are of size 4. Tags may be up to 4 bytes long. Excess bytes can
13 // be used to store additional information about the tag.
14 type Index string
15
16 // Elem returns the element data at the given index.
17 func (s Index) Elem(x int) string {
18         return string(s[x*4 : x*4+4])
19 }
20
21 // Index reports the index of the given key or -1 if it could not be found.
22 // Only the first len(key) bytes from the start of the 4-byte entries will be
23 // considered for the search and the first match in Index will be returned.
24 func (s Index) Index(key []byte) int {
25         n := len(key)
26         // search the index of the first entry with an equal or higher value than
27         // key in s.
28         index := sort.Search(len(s)/4, func(i int) bool {
29                 return cmp(s[i*4:i*4+n], key) != -1
30         })
31         i := index * 4
32         if cmp(s[i:i+len(key)], key) != 0 {
33                 return -1
34         }
35         return index
36 }
37
38 // Next finds the next occurrence of key after index x, which must have been
39 // obtained from a call to Index using the same key. It returns x+1 or -1.
40 func (s Index) Next(key []byte, x int) int {
41         if x++; x*4 < len(s) && cmp(s[x*4:x*4+len(key)], key) == 0 {
42                 return x
43         }
44         return -1
45 }
46
47 // cmp returns an integer comparing a and b lexicographically.
48 func cmp(a Index, b []byte) int {
49         n := len(a)
50         if len(b) < n {
51                 n = len(b)
52         }
53         for i, c := range b[:n] {
54                 switch {
55                 case a[i] > c:
56                         return 1
57                 case a[i] < c:
58                         return -1
59                 }
60         }
61         switch {
62         case len(a) < len(b):
63                 return -1
64         case len(a) > len(b):
65                 return 1
66         }
67         return 0
68 }
69
70 // Compare returns an integer comparing a and b lexicographically.
71 func Compare(a string, b []byte) int {
72         return cmp(Index(a), b)
73 }
74
75 // FixCase reformats b to the same pattern of cases as form.
76 // If returns false if string b is malformed.
77 func FixCase(form string, b []byte) bool {
78         if len(form) != len(b) {
79                 return false
80         }
81         for i, c := range b {
82                 if form[i] <= 'Z' {
83                         if c >= 'a' {
84                                 c -= 'z' - 'Z'
85                         }
86                         if c < 'A' || 'Z' < c {
87                                 return false
88                         }
89                 } else {
90                         if c <= 'Z' {
91                                 c += 'z' - 'Z'
92                         }
93                         if c < 'a' || 'z' < c {
94                                 return false
95                         }
96                 }
97                 b[i] = c
98         }
99         return true
100 }