golang 全角半角相互转换
收藏

中文世界常需要全角转半角或半角转全角的功能,记录一下用 golang 实现的方法。

第一种,利用 unicode 编码,直接计算

// 全角转半角
func DBC2SBC(s string) string {
	var strLst []string
	for _, i := range s {
		insideCode := i
		if insideCode == 12288 {
			insideCode = 32
		} else {
			insideCode -= 65248
		}
		if insideCode < 32 || insideCode > 126 {
			strLst = append(strLst, string(i))
		} else {
			strLst = append(strLst, string(insideCode))
		}
	}
	return strings.Join(strLst, "")
}

第二种,使用 stringsToUpperSpecialToLowerSpecial 来实现

s := `。,()-1!@234567890abc123456789abc`
numConv := unicode.SpecialCase{
	unicode.CaseRange{
		Lo:0x3002, // Lo 全角句号
		Hi:0x3002, // Hi 全角句号
		Delta:[unicode.MaxCase]rune{
			0,               // UpperCase
			0x002e - 0x3002, // LowerCase 转成半角句号
			0,               // TitleCase
		},
	},
	//
	unicode.CaseRange{
		Lo:0xFF01, // 从全角!
		Hi:0xFF19, // 到全角 9
		Delta:[unicode.MaxCase]rune{
			0,               // UpperCase
			0x0021 - 0xFF01, // LowerCase 转成半角
			0,               // TitleCase
		},
	},
}

fmt.Println(strings.ToLowerSpecial(numConv, s))

解释一下:

// ToUpperSpecial 将 s 中的所有字符修改为其大写格式。
// 优先使用 _case 中的规则进行转换
func ToUpperSpecial(_case unicode.SpecialCase, s string) string

// ToLowerSpecial 将 s 中的所有字符修改为其小写格式。
// 优先使用 _case 中的规则进行转换
func ToLowerSpecial(_case unicode.SpecialCase, s string) string

// ToTitleSpecial 将 s 中的所有字符修改为其 Title 格式。
// 优先使用 _case 中的规则进行转换
func ToTitleSpecial(_case unicode.SpecialCase, s string) string

_case 规则说明,以下列语句为例:
unicode.CaseRange{'A', 'Z', [unicode.MaxCase]rune{3, -3, 0}}
·其中 'A', 'Z' 表示此规则只影响 'A' 到 'Z' 之间的字符。
·其中 [unicode.MaxCase]rune 数组表示:
当使用 ToUpperSpecial 转换时,将字符的 Unicode 编码与第一个元素值(3)相加
当使用 ToLowerSpecial 转换时,将字符的 Unicode 编码与第二个元素值(-3)相加
当使用 ToTitleSpecial 转换时,将字符的 Unicode 编码与第三个元素值(0)相加

上面两种比较复杂,特别是第二种,他们都需要这么一张unicode编码表:

unicode编码表

为了简单,建议使用下面第三种方式:

import "golang.org/x/text/width"

s := `。,()-1!@234567890abc123456789abc`
// 全角转半角
fmt.Println(width.Narrow.String(s))
// 半角转全角
fmt.Println(width.Widen.String(s))

这样使用golang 来做字符串的全半角相互转换极为方便。

Relative Articles

官方公众号