[英]Calling a 'dynamic' Object of a HashMap
我剛遇到要在HashMap中調用對象函數的問題。 我已經對其進行了搜索,找到了一個線程,但可惜我不理解。
所以這是我的代碼
public class Seat {
//some attributes
public int getNumber() {
return number;
}
public boolean isReserved() {
return status;
}
}
public class Hall {
private HashMap mySeats;
public HashMap getMeinePlaetze() {
return meinePlaetze;
}
public void createSeats() {
for (int i = 1; i <= this.getnumberOfSeats(); i++) {
this.getMySeats().put(i, new Seat(i, 1));
}
}
}
public class Main {
Hall h1 = new Hall(...);
h1.createSeats();
h1.getMySeats().get(2).isReserved(); //How do I have to write this to work out?
}
我希望我的意圖是合理的。 如果我的代碼很爛,請隨時糾正我。 我已經為此道歉。
非常感謝你。
從版本5開始,Java具有稱為Generics的功能。 您可以在網上找到很多有關泛型的信息,從文章,博客文章等到StackOverflow上的非常好的答案。
泛型允許Java成為強類型語言。 這意味着Java中的變量不僅可以聲明為某種類型(即HashMap
),而且還可以聲明為某種類型以及一個或多個通用類型參數 (即HashMap<K, V>
,其中K
表示類型)圖的鍵的參數, V
代表圖的值的類型參數)。
在您的示例中,您使用的是原始HashMap
(原始類型是允許指定泛型類型參數的類型,但是開發人員尚未指定它們)。 正如您現在所遇到的那樣,原始類型被認為是不好的做法,並且很容易出錯。
HashMap
允許兩個通用類型參數(一個用於鍵,另一個用於值)。 在您的情況下,您將Integer
用於鍵,將Seat
用於值。 簡而言之,您是將整數映射到席位,或者也可以說您的映射是整數到席位的映射。
因此,在Hall
類中,應使用其通用類型參數定義地圖:
private Map<Integer, Seat> mySeats = new HashMap<>();
然后,此代碼:
h1.getMySeats().get(2)
將返回一個Seat
類型的實例,因為您的地圖已經知道其所有值都為Seat
類型。
所以你的代碼:
h1.getMySeats().get(2).isReserved();
可以正常編譯,並且不會出現任何錯誤。
請注意,除了聲明地圖的通用類型外,我還更改了兩點。
首先,我使用其構造函數創建了一個HashMap
的實際實例:
mySeats = new HashMap<>()
如果不使用new
創建您的類型的實例,則以后將不會再有任何HashMap
實例放置您的位置,並且您將獲得NullpointerException
(嘗試!)。
其次,我將變量的類型從HashMap
更改為Map
。 HashMap
是一個類,而Map
只是一個接口。 事實是HashMap
類實現了Map
接口,因此,除非您的代碼明確需要訪問未在Map
接口中聲明的HashMap
方法(這幾乎是不可能的),否則使用mySeats
變量就可以了的類型為Map<Integer, Seat>
而不是HashMap<Integer, Seat>
。 這就是所謂的接口編程,它是您從一開始就應該接受的最佳實踐。 它將在將來為您節省很多麻煩。
h1.getMySeats().get(2).isReserved();
請使用像IntelliJ IDEA這樣的IDE。 它會告訴您一些錯誤,例如在鍵入時忘記括號。
遵循我在注釋中的提示,我不會使用Map將有意義的行或數字鏈接到map-key或array-index。
因此,實際上我會這樣做(因為您問過,我對小費的意思):
座位:
public class Seat {
private final int row;
private final int number;
private boolean reserved = false;
public Seat(int row, int number) {
this.row = row;
this.number = number;
}
public boolean reserve() {
if (!reserved) {
reserved = true;
return reserved;
}
return !reserved;
}
public int getRow() {
return row;
}
public int getNumber() {
return number;
}
public boolean isReserved() {
return reserved;
}
public boolean is(int row, int number) {
return this.row == row && this.number == number;
}
@Override
public int hashCode() {
int hash = 7;
hash = 23 * hash + this.row;
hash = 23 * hash + this.number;
return hash;
}
@Override
public boolean equals(Object obj) {
if (this == obj) {
return true;
}
if (obj == null) {
return false;
}
if (getClass() != obj.getClass()) {
return false;
}
final Seat other = (Seat) obj;
if (this.row != other.row) {
return false;
}
return number == other.number;
}
}
大廳:
public class Hall {
public final Set<Seat> seats = new HashSet<>();
public Set<Seat> getSeats() {
return Collections.unmodifiableSet(seats);
}
public void createSeats(int lastRow, int seatsPerRow) { // This is an example; in case you have different count of seats per row, you better make an boolean addSeat(int row, int number) function; boolean to check if it has been added or if the seat already exists
for (int row = 1; row <= lastRow; row++) {
for (int number = 1; number <= seatsPerRow; number++) {
seats.add(new Seat(row, number));
}
}
}
public Seat get(int row, int number) {
for (Seat seat : seats) { // or you use seats.iterator; I personally hate Iterators; it is my subjective point of view.
if (seat.is(row, number)) {
return seat;
}
}
return null;
}
public boolean reserve(int row, int number) {
Seat seat = get(row, number);
if (seat != null) {
return seat.reserve();
}
return false;
}
}
而我的試駕:
public class TestDrive {
public static void main(String[] args) {
Hall hall = new Hall();
int lastRow = 15;
int seatsPerRow = 10;
hall.createSeats(lastRow, seatsPerRow);
boolean reserved = hall.reserve(5, 9);
System.out.println("Seat(Row=5, Number=9) is reserved: " + (reserved == hall.get(5, 9).isReserved()));
boolean reservedAgain = hall.reserve(5, 9);
System.out.println("Seat(Row=5, Number=9) cannot be reserved again: " + (reservedAgain != hall.get(5, 9).isReserved()));
}
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.