所以,我现在已经在这个问题上坐了好几个小时了,而且我已经没有想法了。我查看了文档(ArrayList和Object)并阅读了很多关于ArrayList.remove(Object obj)
的Stackoverflow问题,但没有任何帮助。
我尝试实现模拟(游戏?),我有一个Cell [] []来存储地图。每个Cell都有一个存储在ArrayList中的居民(Person类),每次迭代都会移动一步。当一个人移动时,我将它们添加到下一个Cell并从旧的Cell中删除它们。或者更确切地说,因为删除部分还没有工作。
我的问题:我需要帮助实现ArrayList.remove(Object obj)方法 到目前为止我得到了什么:
class Cell
{
private final int x;
private final int y;
ArrayList<Person> inhabs = new ArrayList<Person>();
/** this method is called by a Person that wants to move to another Cell **/
public void moveMe(Person p){
try{
Cell northOfHere = grid.grid[y-1][x]//direction will be changed to be random
northOfHere.add(p);
}catch(ArrayIndexOutOfBoundsException ex){/*person falls from the edge of the world*/}
inhabs.remove(p); //this is not working right
}
public void add(Person p){
inhabs.add(p);
}
}
班主任:
class Person extends Object
{
private int health;
private int strength;
private int food;
private final int nation;
@Override
public boolean equals(Object obj){
if(obj == null){return false;}
if(obj == this){return true;}
if(!(obj instanceof Person)){return false;}
Person p = (Person)obj;
return p.toString().equals(toString());
}
@Override
public int hashCode(){
return toString().hashCode();
}
@Override
public String toString(){
return String.format("Health: %03d, Strength: %03d, Food: %03d, Nation: %02d", health, strength, food, nation);
}
}
一些关键点:
inhabs.remove(p);
无法正常工作false
。Person.equals(Object obj)
,ArrayList对if(obj == this){return true;}
的第一次迭代始终返回true。我知道这是一个非常具体的问题,但我找不到任何解决ArrayList问题的事情,甚至没有查看其中的元素。
编辑:更多代码。可能与问题无关,但无论如何我都会发布它,以供上下文使用。
class Grid{
Cell[][] grid;
public Grid(Cell[][] in){
grid = in; //has some cells with people in it.
}
//simply iterates over all cells
public void tick(){
for(int y = 0; y<grid.length; y++){
for(int x = 0; x<grid[y].length; x++){
grid[y][x].tick();
}
}
}
class Cell
{
Grid grid;
public Cell(/*some constants constants*/ Grid g, ArrayList<Person> inh){
grid = g;
if(inh == null){
inhabs = new ArrayList<Person>();
}else{
inhabs = inh;
}
}
//tells every person to make a step
public void tick(){
for(Person p : inhabs.toArray(new Person[inhabs.size()])){
p.tick();
}
}
//and all the other methods from above, of course
}
class Person extends Object
{
Cell cell;
public Person(Cell c, int h, int s, int f, int n){
cell = c;
health = h;
strength = s;
food = f;
nation = n;
}
public void tick(){
//for testing, later more options
cell.moveMe(this);
}
//and all the other methods from above, of course
}
答案 0 :(得分:0)
这是不可复制的,这是一个小逻辑测试:
public static void main(String args[]) {
Person p1 = new Person(10, 2, 2, 1);
Person p2 = new Person(10, 2, 2, 2);
Person p3 = new Person(10, 2, 2, 3);
List<Person> list = new ArrayList<Person>();
list.add(p1);
list.add(p2);
list.add(p3);
System.out.println(list.remove(p2)); //true
System.out.println(list.remove(p2)); //false
System.out.println(list.remove( new Person(10, 2, 2, 3))); //true
}
我的猜测是你没有使用正确的Person
,你要么构造一个新实例而不正确地给出每个变量。 (请注意,您没有在此处提供构造函数,值为final
,这无法正常工作...)
我已经阅读了你的代码。你的问题很简单。
tick
Cell
tick
Person
Cell
Person
Cell
。在那里,您使用Cell.moveMe(Person p);
从当前Cell.inhabs
移动Person
。您确实在新Cell
中移动实例并将其从当前实例中删除。 但是,因为您同时引用了所有实例,所以public void tick(){
//for testing
cell.moveMe(this);
}
从未被指示移动cell
...所以当您致电时:
cell
public Cell moveMe(Person p){
Cell northOfHere = null;
try{
northOfHere = grid.grid[y-1][x];
northOfHere.add(p);
}catch(ArrayIndexOutOfBoundsException ex){
System.out.println("fell from edge");/*person falls from the edge of the world*/
}
System.out.format("Remove from %s person %s%n", this, p);
System.out.println("removed: " + inhabs.remove(p));
return northOfHere;
}
仍然是最初的位置......但是public void tick(){
//for testing
cell = cell.moveMe(this);
}
没有抓住那个人,所以它无法删除收到的实例。
一个简单的修正就是将你移动到的单元格返回:
cell
并更新该单元格:
null
我同意将function fadeInOut(element) {
$(element).fadeIn("slow", function() {
$(this).fadeOut("slow");
})
}
function displayStepWords() {
$('.stepWord').each(function(i) {
var me = $(this);
setTimeout( function(){fadeInOut(me);}, 1000 * i );
})
}
displayStepWords();
保留在<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div class="stepWord">BYE</div>
<div class="stepWord">BY</div>
<div class="stepWord">B</div>
<div class="stepWord">BY</div>
<div class="stepWord">BYE</div>
,当他感觉不在地图时,因为它仍在任何单元格之外。
答案 1 :(得分:0)
Andy Turner指出,您需要修复equals()
方法。在Person
班级中,equals()
必须准确无误。
hashCode()
和equals()
之间有一个contract:如果一个对象等于另一个,则他们的hashCode()
必须相同。因此,最简单的方法是在equals()
上搭载toString()
:
class Person // automatically extends Object
{
// ...
@Override
public boolean equals(Object obj) {
return (obj instanceof Person) && // instanceof is null-safe
this.toString().equals((Person) obj).toString();
}
}
老实说,我不喜欢 编写 equals()
和hashCode()
方法,除非绝对必要。它们很麻烦且容易出错。在这种情况下,它看起来并不绝对必要。有几种选择:
EqualsBuilder
和HashCodeBuilder
。 Here就是一个很好的例子。使用HashCodeBuilder
,您可以编写如下代码:
@Override
public int hashCode() {
return new HashCodeBuilder()
.append(this.health)
.append(this.strength)
...
.toHashCode();
}
使用EqualsBuilder
,您可以编写如下代码:
@Override
public boolean equals(Object obj) {
if (obj instanceof Person == false)
{
return false;
}
if (this == obj)
{
return true;
}
Person that = (Person) obj;
return new EqualsBuilder()
.append(this.health, that.health)
.append(this.strength, that.strength)
...
.isEquals();
}