Java中逆序的基数排序

Posted

技术标签:

【中文标题】Java中逆序的基数排序【英文标题】:Radix sort with reverse order in Java 【发布时间】:2017-05-03 16:02:00 【问题描述】:

我无法理解基数排序。我应该把单词的最后一个字母从右到左排序,直到没有剩下的字母为止。

文本文件如下所示

酒吧 猫 苹果 漏洞 齿轮 跳跃 鹿茸 踝 承担

我的输出是这样的

脚踝 鹿茸 苹果 酒吧 熊 漏洞 跳跃 猫 齿轮

但我应该得到这样的输出

酒吧 漏洞 猫 齿轮 熊 踝 苹果 跳跃 鹿茸

感觉就像我接近拥有正确的代码,但我被卡住了,不知道还能做什么。如果我能得到帮助并指出正确的方向,将不胜感激

这是我所做的代码

RadixSort.java

  public class RadixSort 
      public static void main(String[]args) throws FileNotFoundException
    Linkedlist[] allNameLinkedList = new Linkedlist[26]; // create an array 
        of LinkedList for 26 letters in alphabets
    int count = 0;
    // initialize all the elements in the array to new LinkedList
    for (int i = 0; i < allNameLinkedList.length; i++) 
        allNameLinkedList[i] = new Linkedlist();
    
    Scanner scan = new Scanner(new File("words.txt"));

    while(scan.hasNextLine())
    
        String currentname = scan.nextLine();
        for(int i = 0; i < 26; i++)
            if(currentname.charAt(2) == (char)(i+97))
            
                allNameLinkedList[i].addNodeToTheEndOfTheList(currentname);
            
        
        count++;
    

    // copy sorted nodes to new LinkedList called container
    Linkedlist container = new Linkedlist();
    for (int i = 0; i < 26; i++) 
        Node n = allNameLinkedList[i].front;

        while(n != null)
            container.addNodeToTheEndOfTheList(n.name);
            n = n.next;
        
    
    // empty all the elements of array
    for (int i = 0; i < allNameLinkedList.length; i++) 
        allNameLinkedList[i] = new Linkedlist();
    

    Node m = container.front;
    while(m!=null)
    
        String currentname = m.name;
        for(int i = 0; i < 26; i++)
            if(currentname.charAt(1) == (char)(i+97))
            
                allNameLinkedList[i].addNodeToTheEndOfTheList(currentname);
            
        
        m = m.next;
        count++;
    
    container = new Linkedlist();
    for (int i = 0; i < 26; i++) 
        m = allNameLinkedList[i].front;

        while(m!=null)
            container.addNodeToTheEndOfTheList(m.name);
            m = m.next;
        
    
    for (int i = 0; i < allNameLinkedList.length; i++) 
        allNameLinkedList[i] = new Linkedlist();
    
    m = container.front;

    while(m!=null)
    
        String currentname = m.name;

        for(int i = 0; i < 26; i++)
            if(currentname.charAt(0) == (char)(i+97))
            
                allNameLinkedList[i].addNodeToTheEndOfTheList(currentname);
            
        
        m = m.next;
        count++;
    
    container = new Linkedlist();
    for (int i = 0; i < 26; i++) 
        m = allNameLinkedList[i].front;

        while(m!=null)
            System.out.println(m.name);
            container.addNodeToTheEndOfTheList(m.name);
            m = m.next;
        
    
    scan.close();
    System.out.println("The total number of comparisions was :"+count);
    
    

【问题讨论】:

为了将来参考,明智的做法是包含一个简短的、独立的、正确的示例,该示例以最少的文本显示出了什么问题。这将包括您的链表代码。如需了解更多信息,请查看sscce.org 代码太多,我不太明白你的问题,你对单词进行了排序,你真正需要什么? output you should get 与基数排序有什么关系? 【参考方案1】:

您的问题是只对第一个字符进行排序。

while(m!=null)
    
        String currentname = m.name;

        for(int i = 0; i < 26; i++)
            // charAt(0) is first character in String
            if(currentname.charAt(0) == (char)(i+97)) 
            
                allNameLinkedList[i].addNodeToTheEndOfTheList(currentname);
            
        
        m = m.next;
        count++;
    

您必须遍历每个字符,而不仅仅是第一个字符。这解释了为什么您的排序是按字母顺序排列的。它是如何以完美的字典顺序排列的,这超出了我的理解。代码 sn-p 只会根据 charAt(0) 将数据排序到它们的链表“buckets”中。

您的输入和输出似乎没有加起来,因为输入未排序,而您的输出实际上是您应该具有的字母基数排序:MSD 基数排序。

最重要的数字是您想要进行字母比较的数字,因为在字典顺序的情况下,较高的比较量级是第一个字符。其他排序可能是 LSD(最低有效位),如整数比较,但您应该注意 LSD 基数排序在此处不足,因为您必须担心不同长度的字符串。

使用 MSD 基数排序,没什么大不了的。您只需确保不超出单词的范围,并且在放置后不要移动它,除非它被另一个单词移动。使用 LSD,您必须向后索引,首先检查您的 current word length - current index &gt; 0 是否在继续使用您的实际 charAt 为 charAt(word length - current index) 进行排序,但您的最终结果可能永远不会真正按字母顺序排序 - 我认为 LSD 基数排序对字母顺序的意义不大除非您可以以这种方式订购的概念验证或以这种方式专门分配给您的作业,以便您的最终结果只是部分订购。

其次,您在每次迭代后进行排序的逻辑似乎并不存在。您必须在每次迭代时从每个存储桶中进行排序,以确保所有内容都按排序顺序。

【讨论】:

以上是关于Java中逆序的基数排序的主要内容,如果未能解决你的问题,请参考以下文章

基数排序(Java)

java方式实现基数排序

基数排序算法的Java实现

基数排序(java)

Java八大排序之基数排序

数据结构Java版之基数排序