对于一个数组或者列表或者集合的元素进行排序是一个比较常用的需求。现有的Java类库也提供了API来实现这样的功能,比如Arrays.sort以及Collections.sort的方法。另外,我们也可以用Collator来实现中文的排序。 

Java代码  

日文字符如何排序出来java 日文字母顺序表_java



1. package
2.   
3. import
4. import
5. import
6. import
7. import
8.   
9. public class
10.   
11. public static void
12.   
13. new
14. "中");  
15. "文");  
16. "拼");  
17. "音");  
18. "鑫");  
19. "犇");  
20.   
21.         Collections.sort(list, Collator.getInstance(Locale.CHINA));  
22.   
23. for(String ele: list)  
24.         {  
25.             System.out.println(ele);  
26.         }  
27.   
28.     }  
29. }




输出的结果是: 


拼 


文 


音 


中 


鑫 



 



中文排序后的结果,并不完全正确。

 



这是因为Java使用的是Unicode编码,而常用的中文编码是GB2312,它包含了7000个字符集而且是按照拼音排序的,也是连续的。GB18030和GBK都是在此基础上扩展起来的,这样就会造成Unicode的不连续性,最终导致对有些中文字符排序不完全正确的结果。 




为了能够更好地对中文进行排序,我们可以采用拼音或者笔画来对中文进行排序。本文采用了拼音来排序。将汉语转换成拼音的开源项目有PinYin4j,下载的地址如下: 




Java代码  

日文字符如何排序出来java 日文字母顺序表_java


    1. package
    2.   
    3. import
    4. import
    5. import
    6. import
    7. import
    8. import
    9. import
    10.   
    11. public final class
    12.   
    13. private
    14.     }  
    15.       
    16. /**
    17.      * 判断一个字符是否是中文字符
    18.      */
    19. private static boolean isChineseCharacter(char
    20. return String.valueOf(c).matches("[\\u4E00-\\u9FA5]+");  
    21.     }  
    22.   
    23. /**
    24.      * 将一个含有中文的字符串转换成拼音。
    25.      * Note: 这里只是将中文转换成拼音,其它的各种字符将保持原来的样子。
    26.      */
    27. public static
    28.   
    29. if (null
    30. return null;  
    31.         }  
    32.   
    33. new
    34. char[] charArray = aChineseValue.toCharArray();  
    35.   
    36. new
    37.         outputFormat.setCaseType(HanyuPinyinCaseType.LOWERCASE);  
    38.         outputFormat.setVCharType(HanyuPinyinVCharType.WITH_V);  
    39.         outputFormat.setToneType(HanyuPinyinToneType.WITHOUT_TONE);  
    40.   
    41. for (int i = 0; i < charArray.length; i++) {  
    42. if
    43. try
    44.                     sb.append(PinyinHelper.toHanyuPinyinStringArray(  
    45. 0]);  
    46. catch
    47.                     e.printStackTrace();  
    48.                 }  
    49. else
    50.                 sb.append(charArray[i]);  
    51.             }  
    52.         }  
    53. return
    54.     }  
    55.   
    56. /**
    57.      * 将一个含有中文的字符串转换成拼音。
    58.      * Note: 这里只是将中文转换成拼音,其它的各种字符将保持原来的样子。
    59.      * 
    60.      * 在這裡多了一個參數needToCorrectSpelling,这个主要用于调整姓氏的发音。
    61.      * 如 '单', 这个字作为姓氏念 shan, 但同时也有dan的发音等。
    62.      * 
    63.      * 为了保证姓氏发音的正确性,将了这个参数和相关的简单逻辑
    64.      */
    65. public static
    66. boolean
    67.   
    68. if (null
    69. return null;  
    70.         }  
    71.   
    72. new
    73. char[] charArray = aChineseValue.toCharArray();  
    74.   
    75. new
    76.         outputFormat.setCaseType(HanyuPinyinCaseType.LOWERCASE);  
    77.         outputFormat.setToneType(HanyuPinyinToneType.WITHOUT_TONE);  
    78.         outputFormat.setVCharType(HanyuPinyinVCharType.WITH_V);  
    79.   
    80. null;  
    81. for (int i = 0; i < charArray.length; i++) {  
    82. if
    83. try
    84. if (needToCorrectSpelling && 0
    85.                         surname = SurnameDictionary  
    86.                                 .populateCorrectSpelling(charArray[i]);  
    87. if (null
    88.                             sb.append(PinyinHelper.toHanyuPinyinStringArray(  
    89. 0]);  
    90. else
    91.                             sb.append(surname);  
    92.                         }  
    93. else
    94.                         sb.append(PinyinHelper.toHanyuPinyinStringArray(  
    95. 0]);  
    96.                     }  
    97.   
    98. catch
    99.                     e.printStackTrace();  
    100.                 }  
    101. else
    102.                 sb.append(charArray[i]);  
    103.             }  
    104.         }  
    105. return
    106.     }  
    107.   
    108. public static void main(String[] args) throws
    109. "拼音4j%^**Cool12568 カ キ ";  
    110.         System.out.println(populatePinYing(x));  
    111.     }  
    112. }





    本文的一个简单例子是对名字进行排序,所以下面创建两个类 User 和 NameComparator 


    Java代码  

    日文字符如何排序出来java 日文字母顺序表_java



      1. package
      2.   
      3. import
      4.   
      5. public class User implements
      6.   
      7. private static final long
      8.   
      9. private
      10.   
      11. private int
      12.   
      13. /**
      14.      * @param name
      15.      * @param age
      16.      */
      17. public User(String name, int
      18. this.name = name;  
      19. this.age = age;  
      20.     }  
      21.   
      22. public
      23.   
      24.     }  
      25.   
      26. /**
      27.      * @return the name
      28.      */
      29. public
      30. return
      31.     }  
      32.   
      33. /**
      34.      * @param name
      35.      *            the name to set
      36.      */
      37. public void
      38. this.name = name;  
      39.     }  
      40.   
      41. /**
      42.      * @return the age
      43.      */
      44. public int
      45. return
      46.     }  
      47.   
      48. /**
      49.      * @param age
      50.      *            the age to set
      51.      */
      52. public void setAge(int
      53. this.age = age;  
      54.     }  
      55.   
      56. }




      Java代码  

      日文字符如何排序出来java 日文字母顺序表_java


      1. package
      2.   
      3. import
      4.   
      5. public class NameComparator implements
      6.   
      7. public int
      8.   
      9.         String name1 = u1.getName();  
      10.         String name2 = u2.getName();  
      11.   
      12. return
      13.                 PinYinUtils.populatePinYing(name2));  
      14.     }  
      15.   
      16. }




      测试代码如下: 



      Java代码  

      日文字符如何排序出来java 日文字母顺序表_java

      Before sorting..... 

      1. package
      2.   
      3. import
      4. import
      5. import
      6.   
      7. public class
      8.   
      9. public static void
      10.   
      11.         run();  
      12.     }  
      13.   
      14. private static void
      15.         List<User> list = prepareTestUserList();  
      16.   
      17.         printListBeforeSorting(list);  
      18.   
      19. new
      20.   
      21.         printListAfteSorting(list);  
      22.     }  
      23.   
      24. private static void
      25. "After sorting.....");  
      26.         printList(list);  
      27.     }  
      28.   
      29. private static void
      30. "Before sorting.....");  
      31.         printList(list);  
      32.     }  
      33.   
      34. private static void
      35. for
      36.             System.out.println(user.getName());  
      37.         }  
      38.     }  
      39.   
      40. private static
      41. new
      42. new
      43. "张三");  
      44. 21);  
      45.         list.add(u);  
      46.   
      47. new
      48. "李四");  
      49. 18);  
      50.         list.add(u);  
      51.   
      52. new
      53. "王五");  
      54. 25);  
      55.         list.add(u);  
      56.   
      57. new
      58. "鑫鑫");  
      59. 89);  
      60.         list.add(u);  
      61.   
      62. new
      63. "范范");  
      64. 89);  
      65.         list.add(u);  
      66.   
      67. new
      68. "单一号");  
      69. 89);  
      70.         list.add(u);  
      71.   
      72. new
      73. "犇犇");  
      74. 89);  
      75.         list.add(u);  
      76.   
      77. return
      78.     }  
      79.   
      80. }


      张三 


      李四 


      王五 


      鑫鑫 


      范范 


      单一号 


      犇犇 


      After sorting..... 


      犇犇 


      单一号

       


      范范 


      李四 


      王五 


      鑫鑫 


      张三 



      从上述的排序结果,可以看出“单一号”并没有在一个准确的位置上。产生这种情况是因为中文存在多音字,而且姓氏中的发音会不一样。如“单”在姓氏中需要发“shan”,用PinYin4j能够返回多音字,因为不知道哪一个正确,我在代码中返回了第一个 “dan”。

       


      为了能够保证姓氏发声的正确性,个人想到的有三种:

      1. 数据库中存储姓氏发音的表 

      2. 将姓氏的发音存储在一个key-value的properties文件中 

      3. 创建一个姓氏发音的字典类

       


      本文简单采用第三种方式来实现: 




      Java代码  

      日文字符如何排序出来java 日文字母顺序表_java


      1. package
      2.   
      3.   
      4. public class
      5.   
      6. public static String populateCorrectSpelling(char
      7.   
      8. //TODO:
      9. if ('单'
      10. return "shan";  
      11.         }  
      12.   
      13. return null;  
      14.     }  
      15.       
      16. }





      比较器中加入参数,将SurnameDictionary运用上去。 



      Java代码  

      日文字符如何排序出来java 日文字母顺序表_java



      1. package
      2.   
      3. import
      4.   
      5. public class NameComparator implements
      6.   
      7. public int
      8.   
      9.         String name1 = u1.getName();  
      10.         String name2 = u2.getName();  
      11.   
      12. return PinYinUtils.populatePinYing(name1, true).compareTo(  
      13. true));  
      14.     }  
      15.   
      16. }




      重新运行结果,我们将得到正确的名字排序结果: 



      Before sorting..... 


      张三 


      李四 


      王五 


      鑫鑫 


      范范 


      单一号 


      犇犇 


      After sorting..... 


      犇犇 


      范范 


      李四 


      单一号

       


      王五 


      鑫鑫 


      张三