You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

90 lines
1.5 KiB

2 years ago
  1. package util
  2. import (
  3. "bytes"
  4. "strings"
  5. "unicode"
  6. "github.com/mozillazg/go-pinyin"
  7. )
  8. func PinyinFirstLetterUpper(hans string) string {
  9. if hans == "" {
  10. return ""
  11. }
  12. py := getPinyin(hans)
  13. return processPolyphones(hans, py)
  14. }
  15. func getPinyin(hans string) string {
  16. a := pinyin.NewArgs()
  17. a.Style = pinyin.FIRST_LETTER
  18. a.Heteronym = true
  19. pys := pinyin.Pinyin(hans, a)
  20. var buffer bytes.Buffer
  21. for _, py := range pys {
  22. buffer.WriteString(strings.ToUpper(py[0]))
  23. }
  24. return buffer.String()
  25. }
  26. var polyphoneDict = map[string][2]rune{
  27. "阿": [2]rune{'A', 'E'},
  28. "参": [2]rune{'C', 'S'},
  29. "长": [2]rune{'C', 'Z'},
  30. "术": [2]rune{'S', 'Z'},
  31. }
  32. // 处理多音字,目前只支持一个汉字两个多音字的处理
  33. func processPolyphones(src, py string) string {
  34. srcRune := []rune(src)
  35. keywordIndex := map[int][2]rune{}
  36. for i, r := range srcRune {
  37. if _, ok := polyphoneDict[string(r)]; ok {
  38. keywordIndex[i] = polyphoneDict[string(r)]
  39. }
  40. }
  41. if len(keywordIndex) == 0 {
  42. return py
  43. }
  44. pyRune := []rune(py)
  45. pyRuneReplaced := make([]rune, len(pyRune))
  46. for i, r := range pyRune {
  47. pyRuneReplaced[i] = r
  48. if rs, ok := keywordIndex[i]; ok {
  49. for _, pr := range rs {
  50. if r != pr {
  51. pyRuneReplaced[i] = pr
  52. break
  53. }
  54. }
  55. }
  56. }
  57. if len(pyRuneReplaced) > 0 {
  58. pyRune = append(pyRune, ',')
  59. pyRune = append(pyRune, pyRuneReplaced...)
  60. }
  61. return string(pyRune)
  62. }
  63. //是否是字母字符串
  64. func IsLetter(s string) bool {
  65. for _, r := range s {
  66. if !unicode.IsLetter(r) {
  67. return false
  68. }
  69. }
  70. return true
  71. }