【问题标题】:Java Bubble Sort method for Object's fields对象字段的Java冒泡排序方法
【发布时间】:2021-05-28 05:18:27
【问题描述】:

我想首先根据 Token 对象的 usedNumber 从大到小对它们进行排序。
然后对于具有相同 usedNumber 的令牌,我想根据它们的优先级编号将它们从小到大排序:
名称优先级 usedNumber
1 3
b 2 4
c 3 0
d 4 3
e 5 3
f 6 4
排序后的版本应该首先更大的 usedNumbers 然后更小的优先级:
b 2 4
f 6 4
1 3
d 4 3
e 5 3
c 3 0
下面的代码没有对它们进行正确排序

public class Token {
    int usedNumber;
    int priority;
    String name;
    public  Queue<Token> reversebubbleSort(Queue<Token> queue)
    {
        int n = queue.size();
        int i;
        int j;
        Token temp;
        boolean swapped;
        for (i = 0; i < n - 1; i++)
        {
            swapped = false;
            for (j = 0; j < n - i - 1; j++)
            {
                int namenumber1 = Integer.parseInt(queue.get(j).priority);
                int namenumber2 = Integer.parseInt(queue.get(j+1).priority);
                int number1 = queue.get(j).getUsedNumber();
                int number2 = queue.get(j+1).getUsedNumber();
                if (((number1^5)-namenumber1) < ((number2^5)-namenumber2))
                {
                    // swap arr[j] and arr[j+1]
                    temp = queue.get(j);
                    queue.set(j, queue.get(j+1));
                    queue.set(j+1, temp);
                    swapped = true;
                }
            }
            // IF no two elements were
            // swapped by inner loop, then break
            if (swapped == false)
                break;
        }
        return queue;
    }

这里的队列类不是来自 java.util。由于我的作业限制,这是我设计的一门课程。 Queue类使用Arraylists来执行。

public class Queue<Token>  {
    private ArrayList<Token> queue;
    public Queue() {
        queue = new ArrayList<>();
    }

    public void add(Token addItem){
        //In queues, adding in the back, first in first out.
        queue.add(addItem);
    }
    public void removeFromFront(){
        queue.remove(0);
    }
    public int size(){
        return queue.size();
    }


    public Token get(int location){
        return queue.get(location);
    }
    public void remove(int index){
        queue.remove(index);
    }

    public void set(int location, Token setItem) {
        queue.set(location, setItem);
    }
}
}

【问题讨论】:

  • 您的作业需要实现这种冒泡排序还是仅仅对队列进行排序?
  • 不需要实现冒泡排序。可以使用不同的排序方法进行排序@julien.giband
  • 您究竟希望number1^5 产生什么?

标签: java bubble-sort


【解决方案1】:
  • 与其将ArrayList 包装在您的Queue 中,不如扩展它:使代码更简单
  • 不要使用“Token”作为通用类名:这会造成混淆。而是使用标准 T 它为您提供 Queue.java 的代码:
import java.util.ArrayList;

/*
 * If it's only ever used for Token, it could also be
 * public class Queue extends ArrayList<Token>
 *   and then you could override the sort method of ArrayList
 *   with the implementation shown in Token.sortSpecial below
 */
public class Queue<T> extends ArrayList<T> {

  private static final long serialVersionUID = 1L;

  public void removeFromFront() {
    super.remove(0);
  }

}
  • Token 类中的队列排序方法应该是静态的:它与实例的状态无关。我已将其重命名为 sortSpecial。它也不必返回,因为排序是在Queue 上完成的
  • 使用List.sort 和自定义Comparator 进行排序
  • 使用 getter 和 setter 的字段应该是私有的(此处未显示)

这会给你Token.java

public class Token {

  private String name;
  private int priority;
  private int usedNumber;

  public Token(String name, int priority, int usedNumber) {
    super();
    this.usedNumber = usedNumber;
    this.priority = priority;
    this.name = name;
  }

  /* Getters and Setters go here */

  /** Sort by usedNumber DESC / priority ASC */
  public static void sortSpecial(Queue<Token> queue) {
    queue.sort((x, y) -> {
      int comp = -Integer.compare(x.usedNumber, y.usedNumber);
      if (comp == 0)
        comp = Integer.compare(x.priority, y.priority);
      return comp;
    });
  }
  
  @Override
  public String toString() {
    return getClass().getSimpleName() + "[" + name + " (p=" + priority + ", un=" + usedNumber + ")]";
  }
  
}

或者,如果您想玩聪明的人,您可以将比较器编写为单行(在定义您的 getter 之后):

Comparator.comparingInt(Token::getUsedNumber).reversed().thenComparingInt(Token::getPriority)

程序的入口点(Main.java):

public class Main {
  
  public static void main(String[] args) {
    Queue<Token> toks = new Queue<>();
    toks.add(new Token("a", 1, 3));
    toks.add(new Token("b", 2, 4));
    toks.add(new Token("c", 3, 0));
    toks.add(new Token("d", 4, 3));
    toks.add(new Token("e", 5, 3));
    toks.add(new Token("f", 6, 4));
    
    System.out.println("Input:");
    toks.stream().forEach(t -> System.out.println('\t' + t.toString()));
    System.out.println();
    
    Token.sortSpecial(toks);
    System.out.println("Output:");
    toks.stream().forEach(t -> System.out.println('\t' + t.toString()));
  }

}

控制台输出:

Input:
    Token[a (p=1, un=3)]
    Token[b (p=2, un=4)]
    Token[c (p=3, un=0)]
    Token[d (p=4, un=3)]
    Token[e (p=5, un=3)]
    Token[f (p=6, un=4)]

Output:
    Token[b (p=2, un=4)]
    Token[f (p=6, un=4)]
    Token[a (p=1, un=3)]
    Token[d (p=4, un=3)]
    Token[e (p=5, un=3)]
    Token[c (p=3, un=0)]

【讨论】:

  • 为什么我们在这一行的 sortSpacial 方法中使用“-” int comp = -Integer.compare(x.usedNumber, y.usedNumber);
  • 它将通过返回相反的值来反转自然排序。查看Comparatordocs.oracle.com/javase/8/docs/api/java/util/Comparator.html的文档
  • 基本上-1 表示 x 0 表示 x = y,+1 表示 y > x。反转所有这些比较,您的列表将向后排序
  • 更正:-1 表示 x 0 表示 x = y,+1 表示 y x
猜你喜欢
  • 2020-04-21
  • 2021-06-10
  • 1970-01-01
  • 1970-01-01
  • 2013-09-04
  • 1970-01-01
  • 2022-11-29
  • 2014-06-25
  • 2017-04-05
相关资源
最近更新 更多