java - 通用对象链表 (Java)

标签 java list object generics

我是 Java 的新手,这是我使用它的第二堂课(在大学里)。在学期开始时,我创建了一个简单的类来表示僵尸,其中包含它们的年龄、类型和名称。后来,我做了一个整数链表。现在,我需要制作一个可以容纳这些“僵尸”的通用链表。我还必须制作一个菜单,允许我添加、删除、计数和显示“僵尸”。我已经盯着它看了好几个小时,翻阅我的书,并在网上寻找我的问题的答案。我可以添加和显示这些“僵尸”,但在列表中计算它们并尝试删除它们只是告诉我输入的参数没有。换句话说,我比较“僵尸”的方式可能有问题。这是我的代码。我知道这是一个很好的 300 行代码来浏览......但我没有想法。

僵尸.java

public class Zombie
{
private String zAge;
private String zType;
private String zName;

public Zombie(String zA, String zT, String zN)
{
    zAge = zA;
    zType = zT;
    zName = zN;
}

public void setZAge(String zA)
{
    zAge = zA;
}

public void setZType(String zT)
{
    zType = zT;
}

public void setZName(String zN)
{
    zName = zN;
}

public String getZAge()
{
    return zAge;
}

public String getZType()
{
    return zType;
}

public String getZName()
{
    return zName;
}

public boolean equals(Zombie zomb)
{
    if(zomb.getZAge() == zAge && zomb.getZType() == zType && zomb.getZName() == zName)
        return true;
    else
        return false;
}
}

LinkedBag.java

public class LinkedBag<E>
{
//Head node and number of nodes in bag
private Node<E> head;
private int manyNodes;

//Constructor
public LinkedBag()
{
    head = null;
    manyNodes = 0;
}

//Returns the number of nodes in the bag
public int getSize()
{
    return manyNodes;
}

//Returns the node that is at the head of the linked list
public Node<E> getListStart()
{
    return head;
}

//Adds a node to the beginning of the list
public void add(E element)
{
    head = new Node<E>(element,head);       //Creates a new node pointing to the head and sets the head of the linked bag to the new Node
    manyNodes++;        //Increments Node counter
}

//Counts the number of times Node [target] occurs within the bag
public int countOccurences(E target)
{
    int count = 0;      //Initializes incrementable counter

    if(head==null)      //Checks if bag is empty and returns null if bag is empty
        return 0;

    if(head.getData().equals(target))       //Checks if the head of the linked list is [target]
        count++;            //Increments counter

    Node<E> cursor = head;      //Sets temporary Node [cursor] to the same value and pointer as head

    while(cursor.getLink() != null)     //Loops until the next Node contains no value
    {
        if(cursor.getLink().getData().equals(target))           //Checks if the value of the next Node is [target]
            count++;                //Increments counter

        cursor=cursor.getLink();            //Cursor continues down linked list
    }

    return count;       //Returns incremented int [count], number of occurences of [target]
}

//Checks if Node [target] exists within the bag
public boolean exists(E target)
{
    if(head.getData().equals(target))       //Checks if the head of the linked list is [target]
        return true;

    Node<E> cursor = head;      //Sets temporary Node [cursor] to the same value and pointer as head

    while(cursor.getLink() != null)     //Loops until the next Node contains no value
    {
            if(cursor.getData().equals(target))     //Checks if current Node is [target] and returns true if true
                return true;

            cursor=cursor.getLink();        //Cursor continues down linked list
    }
            return false;       //Returns false if cursor goes through entire linked list and [target] isn't found
}

//Checks if Node [target] exists within the bag and removes the first occurence of it
public boolean remove(E target)
{       
    if(head==null)          //Returns false if bag is empty
        return false;

    if(head.getData().equals(target))   //If the head Node's data is [target]
    {
        head = head.getLink();      //Make the next Node the head
        manyNodes--;            //Decrements Node counter
        return true;            //Returns true, found [target]
    }

    Node<E> cursor = head;          //Sets temporary Node [cursor] to the same value and pointer as head

    while(cursor.getLink() != null)     //Loops until the next Node contains no value
    {
        cursor = cursor.getLink();      //Cursor continues down linked list

        if(cursor.getLink().getData().equals(target))   //If the next node's data is [target]
        {
            cursor.setLink(cursor.getLink().getLink());     //Sets current Node's link to the next Node's link, by passing the next Node
            manyNodes--;            //Decrements Node counter
            return true;            //Returns true, found [target]
        }
    }
    return false;           //Returns false, [target] not found
}
}

节点.java

public class Node<E>
{
private E data;
private Node<E> link;


public Node(E initialData, Node<E> initialLink)
{
    data = initialData;
    link = initialLink;
}

public E getData()
{
    return data;
}

public Node<E> getLink ()
{
    return link;
}

public void setData(E element)
{
    data = element;
}

public void setLink(Node<E> newLink)
{
    link = newLink;
}
}

这是用户与之交互的菜单文件 ZombiesProj2.java

import java.util.Scanner;

public class ZombiesProj2
{
public static void main(String[] args) throws InterruptedException
{
    LinkedBag<Zombie> zBag = new LinkedBag<Zombie>();       //Linked bag to hold Zombie Objects
    String choice = "";

    Scanner input = new Scanner(System.in);

    while(!choice.equalsIgnoreCase("x"))
    {   
        //Menu
        System.out.println("\nSac de Zombi\n");
        System.out.println("S - Display size of bag");
        System.out.println("A - Add 'Zombie' to bag");
        System.out.println("R - Remove 'Zombie' from bag");
        System.out.println("F - Find 'Zombie' in bag");
        System.out.println("D - Display contents of bag");
        System.out.println("X - Exit");
        System.out.print("Enter Selection: ");

        //Input and Output
        choice = input.nextLine();

        if(choice.equalsIgnoreCase("s"))
        {
            System.out.println("\nSize = " + zBag.getSize() + "\n");
        }
        else if(choice.equalsIgnoreCase("a"))       //adds zombie
        {
            String zAge;
            String zType;
            String zName;

            System.out.print("How many years has this zombie ROAMED THE EARTH: ");
            zAge = input.nextLine();
            System.out.print("What type of zombie is it: ");
            zType = input.nextLine();
            System.out.print("What would you like to name this zombie: ");
            zName = input.nextLine();

            Zombie newZomb = new Zombie(zAge,zType,zName);
            zBag.add(newZomb);
        }
        else if(choice.equalsIgnoreCase("r"))       //removes zombie
        {
            String zAge;
            String zType;
            String zName;

            System.out.print("How many years has this zombie ROAMED THE EARTH: ");
            zAge = input.nextLine();
            System.out.print("What type of zombie is it: ");
            zType = input.nextLine();
            System.out.print("What is the name of the zombie: ");
            zName = input.nextLine();

            Zombie rZomb = new Zombie(zAge,zType,zName);

            zBag.remove(rZomb);
        }
        else if(choice.equalsIgnoreCase("f"))       //counts number of matching zombies
        {
            String zAge;
            String zType;
            String zName;

            System.out.print("How many years has this zombie ROAMED THE EARTH: ");
            zAge = input.nextLine();
            System.out.print("What type of zombie is it: ");

            zType = input.nextLine();
            System.out.print("What is the name of the zombie: ");
            zName = input.nextLine();

            Zombie fZomb = new Zombie(zAge,zType,zName);

            System.out.println("The " + zAge + " year old zombie type " + zType + " named " + zName + " occurs " + zBag.countOccurences(fZomb)+ " time(s)");
        }
        else if(choice.equalsIgnoreCase("d"))       //displays entire zombie 'bag'
        {
            Node cursor = zBag.getListStart();
            Zombie dZomb;
            while(cursor !=null)
            {
                dZomb = (Zombie)cursor.getData();
                System.out.print("[Zombie "+dZomb.getZAge()+" "+dZomb.getZType()+" "+dZomb.getZName()+"],");
                cursor = cursor.getLink();
            }
        }
        else if(!choice.equalsIgnoreCase("x"))  
        {
            System.out.println("Error: Invalid Entry");
        }
    }
}
}

更新了 equals 和 hashCode

public boolean equals(Object obj)
{
    if(obj==null)
        return false;
    if(obj==this)
        return true;
    if(obj.getClass() != getClass())
        return false;

    Zombie zomb = (Zombie)obj;
    if(zomb.getZAge().equals(zAge) && zomb.getZType().equals(zType) && zomb.getZName().equals(zName))
        return true;
    else
        return false;
}

public int hashCode() { return 0; }

最佳答案

我知道,因为您正在尝试学习编程,所以您正在编写自己的链表,而不是使用 Java 的 LinkedList。但是,您错过了一些事情。

  1. 您的 equals 方法应该与 Object Zombie.equals(Object) 中的签名相同。而且,如果参数不是 Zombie,它应该做的第一件事是返回 false
  2. 无论何时编写 equals 方法,都必须同时编写 hashCode 方法。查看大多数示例以了解详细信息。
  3. 切勿对字符串使用等于运算符。始终使用 equals 方法。将 zomb.getZAge() == zAge 替换为 zomb.getZAge().equals(zAge)
  4. 为什么 zAge 是一个 String?你可以让它成为某种数字。
  5. 没必要在你的类里面到处写“Z”。它在僵尸中;你的读者知道。在工作中,我有同事坚持在所有变量中重复类名。

这不是好的代码。

public class Document {
    private Long documentId;
    private String documentName;
    private String documentAuthor;
    private Date documentPublicationDate;
    // 10 more instance variables.
    // Constructors, accessors, other code.
}

然后他们将 Document 类型的变量命名为 documentAdocumentB 等。多么无聊、重复和多余。

关于java - 通用对象链表 (Java),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/16127554/

相关文章:

Java lambda,将记录的文本文件(例如CSV)转换为流?

java - 处理这些 if 子句的更简洁的方法?

java - 通过java执行复杂的Titan查询

javascript - 创建绑定(bind)生成的对象的新实例

java - Hazelcast 内置的 CountAggregation 真的效率低下吗?

python - 列表到字典 python

r - data.frames R 列表列表中元素的平均值

java - Java中列表的增量过滤

将方法作为回调传递的 javascript 问题

c# - Guid 是原始类型还是复杂类型?