// IsDigit reports whether the rune is a decimal digit.
func IsDigit(rune int) bool {
- if rune < Latin1Max {
+ if rune <= MaxLatin1 {
return '0' <= rune && rune <= '9'
}
return Is(Digit, rune)
// Test that the special case in IsDigit agrees with the table
func TestDigitOptimization(t *testing.T) {
- for i := 0; i < Latin1Max; i++ {
+ for i := 0; i <= MaxLatin1; i++ {
if Is(Digit, i) != IsDigit(i) {
t.Errorf("IsDigit(U+%04X) disagrees with Is(Digit)", i)
}
func IsGraphic(rune int) bool {
// We cast to uint32 to avoid the extra test for negative,
// and in the index we cast to uint8 to avoid the range check.
- if uint32(rune) < Latin1Max {
+ if uint32(rune) <= MaxLatin1 {
return properties[uint8(rune)]&pg != 0
}
return IsOneOf(GraphicRanges, rune)
// character. This categorization is the same as IsGraphic except that the
// only spacing character is ASCII space, U+0020.
func IsPrint(rune int) bool {
- if uint32(rune) < Latin1Max {
+ if uint32(rune) <= MaxLatin1 {
return properties[uint8(rune)]&pp != 0
}
return IsOneOf(PrintRanges, rune)
// The C (Other) Unicode category includes more code points
// such as surrogates; use Is(C, rune) to test for them.
func IsControl(rune int) bool {
- if uint32(rune) < Latin1Max {
+ if uint32(rune) <= MaxLatin1 {
return properties[uint8(rune)]&pC != 0
}
// All control characters are < Latin1Max.
// IsLetter reports whether the rune is a letter (category L).
func IsLetter(rune int) bool {
- if uint32(rune) < Latin1Max {
+ if uint32(rune) <= MaxLatin1 {
return properties[uint8(rune)]&(pLu|pLl) != 0
}
return Is(Letter, rune)
// IsNumber reports whether the rune is a number (category N).
func IsNumber(rune int) bool {
- if uint32(rune) < Latin1Max {
+ if uint32(rune) <= MaxLatin1 {
return properties[uint8(rune)]&pN != 0
}
return Is(Number, rune)
// IsPunct reports whether the rune is a Unicode punctuation character
// (category P).
func IsPunct(rune int) bool {
- if uint32(rune) < Latin1Max {
+ if uint32(rune) <= MaxLatin1 {
return properties[uint8(rune)]&pP != 0
}
return Is(Punct, rune)
// Z and property Pattern_White_Space.
func IsSpace(rune int) bool {
// This property isn't the same as Z; special-case it.
- if uint32(rune) < Latin1Max {
+ if uint32(rune) <= MaxLatin1 {
switch rune {
case '\t', '\n', '\v', '\f', '\r', ' ', 0x85, 0xA0:
return true
// IsSymbol reports whether the rune is a symbolic character.
func IsSymbol(rune int) bool {
- if uint32(rune) < Latin1Max {
+ if uint32(rune) <= MaxLatin1 {
return properties[uint8(rune)]&pS != 0
}
return Is(Symbol, rune)
// in the Latin-1 range through the property table.
func TestIsControlLatin1(t *testing.T) {
- for i := 0; i < Latin1Max; i++ {
+ for i := 0; i <= MaxLatin1; i++ {
got := IsControl(i)
want := false
switch {
}
func TestIsLetterLatin1(t *testing.T) {
- for i := 0; i < Latin1Max; i++ {
+ for i := 0; i <= MaxLatin1; i++ {
got := IsLetter(i)
want := Is(Letter, i)
if got != want {
}
func TestIsUpperLatin1(t *testing.T) {
- for i := 0; i < Latin1Max; i++ {
+ for i := 0; i <= MaxLatin1; i++ {
got := IsUpper(i)
want := Is(Upper, i)
if got != want {
}
func TestIsLowerLatin1(t *testing.T) {
- for i := 0; i < Latin1Max; i++ {
+ for i := 0; i <= MaxLatin1; i++ {
got := IsLower(i)
want := Is(Lower, i)
if got != want {
}
func TestNumberLatin1(t *testing.T) {
- for i := 0; i < Latin1Max; i++ {
+ for i := 0; i <= MaxLatin1; i++ {
got := IsNumber(i)
want := Is(Number, i)
if got != want {
}
func TestIsPrintLatin1(t *testing.T) {
- for i := 0; i < Latin1Max; i++ {
+ for i := 0; i <= MaxLatin1; i++ {
got := IsPrint(i)
want := IsOneOf(PrintRanges, i)
if i == ' ' {
}
func TestIsGraphicLatin1(t *testing.T) {
- for i := 0; i < Latin1Max; i++ {
+ for i := 0; i <= MaxLatin1; i++ {
got := IsGraphic(i)
want := IsOneOf(GraphicRanges, i)
if got != want {
}
func TestIsPunctLatin1(t *testing.T) {
- for i := 0; i < Latin1Max; i++ {
+ for i := 0; i <= MaxLatin1; i++ {
got := IsPunct(i)
want := Is(Punct, i)
if got != want {
}
func TestIsSpaceLatin1(t *testing.T) {
- for i := 0; i < Latin1Max; i++ {
+ for i := 0; i <= MaxLatin1; i++ {
got := IsSpace(i)
want := Is(White_Space, i)
if got != want {
}
func TestIsSymbolLatin1(t *testing.T) {
- for i := 0; i < Latin1Max; i++ {
+ for i := 0; i <= MaxLatin1; i++ {
got := IsSymbol(i)
want := Is(Symbol, i)
if got != want {
const (
MaxRune = 0x10FFFF // Maximum valid Unicode code point.
ReplacementChar = 0xFFFD // Represents invalid code points.
- ASCIIMax = 0x80 // (1 beyond) maximum ASCII value.
- Latin1Max = 0x100 // (1 beyond) maximum Latin-1 value.
+ MaxASCII = 0x7F // maximum ASCII value.
+ MaxLatin1 = 0xFF // maximum Latin-1 value.
)
// RangeTable defines a set of Unicode code points by listing the ranges of
// Is tests whether rune is in the specified table of ranges.
func Is(rangeTab *RangeTable, rune int) bool {
// common case: rune is ASCII or Latin-1.
- if uint32(rune) < Latin1Max {
+ if uint32(rune) <= MaxLatin1 {
// Only need to check R16, since R32 is always >= 1<<16.
r16 := uint16(rune)
for _, r := range rangeTab.R16 {
// IsUpper reports whether the rune is an upper case letter.
func IsUpper(rune int) bool {
// See comment in IsGraphic.
- if uint32(rune) < Latin1Max {
+ if uint32(rune) <= MaxLatin1 {
return properties[uint8(rune)]&pLu != 0
}
return Is(Upper, rune)
// IsLower reports whether the rune is a lower case letter.
func IsLower(rune int) bool {
// See comment in IsGraphic.
- if uint32(rune) < Latin1Max {
+ if uint32(rune) <= MaxLatin1 {
return properties[uint8(rune)]&pLl != 0
}
return Is(Lower, rune)
// IsTitle reports whether the rune is a title case letter.
func IsTitle(rune int) bool {
- if rune < Latin1Max {
+ if rune <= MaxLatin1 {
return false
}
return Is(Title, rune)
// ToUpper maps the rune to upper case.
func ToUpper(rune int) int {
- if rune < ASCIIMax {
+ if rune <= MaxASCII {
if 'a' <= rune && rune <= 'z' {
rune -= 'a' - 'A'
}
// ToLower maps the rune to lower case.
func ToLower(rune int) int {
- if rune < ASCIIMax {
+ if rune <= MaxASCII {
if 'A' <= rune && rune <= 'Z' {
rune += 'a' - 'A'
}
// ToTitle maps the rune to title case.
func ToTitle(rune int) int {
- if rune < ASCIIMax {
+ if rune <= MaxASCII {
if 'a' <= rune && rune <= 'z' { // title case is upper case for ASCII
rune -= 'a' - 'A'
}
// Check that the optimizations for IsLetter etc. agree with the tables.
// We only need to check the Latin-1 range.
func TestLetterOptimizations(t *testing.T) {
- for i := 0; i < Latin1Max; i++ {
+ for i := 0; i <= MaxLatin1; i++ {
if Is(Letter, i) != IsLetter(i) {
t.Errorf("IsLetter(U+%04X) disagrees with Is(Letter)", i)
}
if *test {
return
}
- fmt.Println("var properties = [Latin1Max]uint8{")
- for code := 0; code < unicode.Latin1Max; code++ {
+ fmt.Println("var properties = [MaxLatin1+1]uint8{")
+ for code := 0; code <= unicode.MaxLatin1; code++ {
var property string
switch chars[code].category {
case "Cc", "": // NUL has no category.
{0x10400, 0x10427, d{0, 40, 0}},
{0x10428, 0x1044F, d{-40, 0, -40}},
}
-var properties = [Latin1Max]uint8{
+var properties = [MaxLatin1 + 1]uint8{
0x00: pC, // '\x00'
0x01: pC, // '\x01'
0x02: pC, // '\x02'