【问题标题】:Can only remove object from index 0 in array只能从数组中的索引 0 中删除对象
【发布时间】:2018-04-04 15:59:42
【问题描述】:

我遇到的问题如下:我创建了两个数组,表示船舶的停靠空间。第一个数组 (dock1[]) 可以将船舶对象(shipName 和大小 - 通常是 Super-Container)保存在数组中。如果我想从 dock1[] 中删除对象,请输入 shipName 以将其删除。

但我只能从数组中的第一个空间(索引 0)中删除 ship 对象,而不能从任何其他空间(即索引 1、2、3)中删除。

你能帮忙吗?这是我的停靠类,在 undock() if 语句中的问题:

import java.util.*;

public class Main {

static Scanner scan = new Scanner(System.in);

private static Ship[] dock1 = new Ship[10];
private static Ship[] waitingList = new Ship[10];

public static void main(String[] args) {
    menu();
}

public static void menu() {


    Scanner scan = new Scanner(System.in);


    while (true) {

        System.out.println("Choose an option: 1-3");
        System.out.println("1. Dock");
        System.out.println("2. Undock");
        System.out.println("3. Status");

        int menu = scan.nextInt();
        switch (menu) {
            case 1:
                System.out.println("1. Dock");
                dock();
                break;
            case 2:
                System.out.println("2. Undock");
                undock();
                break;
            case 3:
                System.out.println("3. Status");
                printDock();
                printWaitingList();
                break;
            case 4:
                System.out.println("4. Exit");
                System.exit(0);
            default:
                System.out.println("No such option");
                break;
        }
    }
}


public static void dock() {

    System.out.println("Enter ship's name: ");
    String name = scan.nextLine();

    System.out.println("Enter ship's size: ");
    String size = scan.nextLine();

    System.out.println("Enter the ships dock:");
    //Check if the dock number is valid
    int i = Integer.valueOf(scan.nextLine());
    if (i >= 0 && i < 10 && dock1[i] == null) {
        int c = 0;
        int co = 0;
        int sco = 0;
        for (int j = 0; j < dock1.length; j++) {
            if (dock1[j] != null && dock1[j].getShipSize().equals("Cargo")) {
                c++;
            }
            if (dock1[j] != null && dock1[j].getShipSize().equals("Container")) {
                co++;
            }
            if (dock1[j] != null && dock1[j].getShipSize().equals("Super-Container")) {
                sco++;
            }
        }

        if (c < 10 && co < 5 && sco < 2) {
            //Add ship to the dock
            dock1[i] = new Ship(name, size);
            System.out.println("Enough space you can dock");
            System.out.println("Ship has been docked");
        } else {
            System.out.println("You cannot dock");
            waitingList(name, size);
        }

    } else {
        System.out.println("Couldn't dock");
        waitingList(name, size);
    }

}


public static void undock() {
    System.out.println("Status of ships: ");
    printDock();
    System.out.println("Enter ship's name to undock: ");
    String name = scan.nextLine();

    for (int i = 0; i < dock1.length; i++) {
        if (dock1[i] != null && dock1[i].getShipName().equals(name)) { //ONLY FINDING in ARRAY 0
            dock1[i] = null;
            System.out.println("Ship removed");
            /// HERE CHECK IF SHIP IN DOCK
            for (int j = 0; j < waitingList.length; j++) {
                if (dock1[i] == null && waitingList[j] != null) {
                    // Add ship to the dock
                    dock1[i] = new Ship(waitingList[j].getShipName(), waitingList[j].getShipSize());
                    System.out.println("Move ship from waiting list to dock 1");
                    waitingList[j] = null;
                    return;
                } else {
                 //   System.out.println("No space in dock");
                    return;
                }
            }
        } else {
            System.out.println("Ship not docked here");
            break;
        }

    }

}

public static void waitingList(String name, String size) {

    System.out.println("Dock 1 is full, ship will try to be added to Waiting List");
    for (int i = 0; i < waitingList.length; i++) {
        if (waitingList[i] == null) {
            //Add ship to the dock
            waitingList[i] = new Ship(name, size);
            System.out.println("Enough space added to waiting list");
            return;
        } else {

        }
    }
    System.out.println("No space on waiting list, ship turned away.");
}

public static void printDock() {

    System.out.println("Docks:");

    for (int i = 0; i < dock1.length; i++) {
        if (dock1[i] == null) {
            System.out.println("Dock " + i + " is empty");
        } else {
            System.out.println("Dock " + i + ": " + dock1[i].getShipName() + " " + dock1[i].getShipSize());
        }
    }
}

private static void printWaitingList() {

    System.out.println("Waiting List:");

    for (int i = 0; i < waitingList.length; i++) {
        if (waitingList[i] == null) {
            System.out.println("Dock " + i + " is empty");
        } else {
            System.out.println("Dock " + i + ": " + waitingList[i].getShipName() + " " + waitingList[i].getShipSize());
        }
    }
}
}

【问题讨论】:

  • 为什么不使用arraylist 并在其上使用remove 或splice 方法。它会让你的代码更短
  • 感谢您的评论。但由于码头是固定大小的,我必须使用一个数组。
  • 你也可以用 arraylist 做到这一点。

标签: java arrays oop


【解决方案1】:

问题是,当一艘船没有停靠在第一个位置(索引 0)时,您将不会检查其他位置,这是因为如果它不等于要停靠的船的名称,您有一个 break 语句。 break 语句终止循环,不再继续检查其他位置。

只需删除 undock 方法中的 break 语句即可。

编辑

你的代码应该是这样的。

 System.out.println("Status of ships: ");
printDock();
System.out.println("Enter ship's name to undock: ");
String name = scan.nextLine();
boolean deleted = false;
for (int i = 0; i < dock1.length; i++) {
    if (dock1[i] != null && dock1[i].getShipName().equals(name)) { //ONLY FINDING in ARRAY 0
        dock1[i] = null;
        System.out.println("Ship removed");
        deleted = true;
        /// HERE CHECK IF SHIP IN DOCK
        for (int j = 0; j < waitingList.length; j++) {
            if (dock1[i] == null && waitingList[j] != null) {
                // Add ship to the dock
                dock1[i] = new Ship(waitingList[j].getShipName(), waitingList[j].getShipSize());
                System.out.println("Move ship from waiting list to dock 1");
                waitingList[j] = null;
                return;
            } else {
                //   System.out.println("No space in dock");
                return;
            }
        }
    }

}
if (!deleted) System.out.println("No ship was removed")

【讨论】:

  • 当我过去使用此方法时,它会移除船,但我仍然得到 else 语句 - System.out.println("Ship not docked here");第一的。我需要一种方法,以便在不获取此声明的情况下将其删除
  • 所以这段代码不应该出现在 else 语句中,因为它会在每次检查要删除的 Ship 不在给定位置时打印它。只有在您检查没有删除任何船只时,才应在最后打印此消息。
  • 我认为不需要删除的标志。请注意,当第一个 if 为真时,OP 在任何情况下都使用硬 return
  • 嘿EduG,你的答案和我基本一样。那一定要奖励+1 :)
  • @luksch 确实如此,但请注意,如果等待码头中没有船,那么它将不会返回循环内,它将继续,然后消息将显示在最后,但是是的,这段代码可以更改很多,并且行数要少得多。
【解决方案2】:

我看到了 2 个错误:

1) 在 undock 方法的 else 语句中中断循环。 2) 如果您在第一个码头找到船名,那么您总是会在 waitingList 循环的第一次迭代中返回。

for (int i = 0; i < dock1.length; i++) {
    if (dock1[i] != null && dock1[i].getShipName().equals(name)) { //ONLY FINDING in ARRAY 0
        dock1[i] = null;
        System.out.println("Ship removed");
        /// HERE CHECK IF SHIP IN DOCK
        for (int j = 0; j < waitingList.length; j++) {
            if (dock1[i] == null && waitingList[j] != null) {
                // Add ship to the dock
                dock1[i] = new Ship(waitingList[j].getShipName(), waitingList[j].getShipSize());
                System.out.println("Move ship from waiting list to dock 1");
                waitingList[j] = null;
                return;
            } else {
             //   System.out.println("No space in dock");
                return;
            }
        }
        // NOTE -> THIS ALWAYS ENDS IN A RETURN
    } else {
        System.out.println("Ship not docked here");
        break;
    }
}

我认为您应该省略 break 语句以便尝试其他扩展坞。另外,测试等待列表时不要返回调用者方法。

所以试试这个:

for (int i = 0; i < dock1.length; i++) {
    if (dock1[i] != null && dock1[i].getShipName().equals(name)) { //ONLY FINDING in ARRAY 0
                      dock1[i] = null;
        System.out.println("Ship removed");
        /// HERE CHECK IF SHIP IN DOCK
        for (int j = 0; j < waitingList.length; j++) {
            if (dock1[i] == null && waitingList[j] != null) {
                // Add ship to the dock
                dock1[i] = new Ship(waitingList[j].getShipName(), waitingList[j].getShipSize());
                System.out.println("Move ship from waiting list to dock 1");
                waitingList[j] = null;
                return;
            } else {
             //   System.out.println("No space in dock, go on in waiting list");
              // NO RETURN HERE
            }
        }
    } else {
        System.out.println("Ship not docked here, try next dock if there is one left");
        // NO BREAK HERE
    }
}
System.out.println("Ship not docked in any dock");

【讨论】:

  • 当我过去使用此方法时,它会移除船,但我仍然得到 else 语句 - System.out.println("Ship not docked here");第一的。我需要一种方法,以便在不获取此声明的情况下将其删除
  • 对不起,现在我失去了你。我不明白你的问题。我认为我的说法是正确的。您的循环将永远不会增加,因为 if 语句为真并且您最终进入 return 或者您最终进入 else 语句并且这将 break 循环。
  • 没有'break;' - 如果我输入要删除的“shipName”,它确实会从数组中删除该船,但我首先从 else 语句“Ship not docked here”中得到消息,然后我得到“ship removed”并且该船已经删除。我需要它,所以我没有得到 else 语句“船舶未停靠在这里”
  • 查看我更改的println,表示现在将在下一个码头搜索该船。如果您只想打印根本找不到它,那么您需要将 println 置于循环之外直到您的方法结束。
  • 我更新了我的答案,因为我认为您的代码中有第二个问题。请检查
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2022-01-19
  • 2019-07-23
  • 2021-06-06
  • 2011-11-29
  • 1970-01-01
  • 1970-01-01
  • 2012-08-26
相关资源
最近更新 更多