web-dev-qa-db-fra.com

Émettre une itération dans ArrayLists

J'ai deux questions. J'ai ici un objet de type ArrayList et, dans ce cas, appelons-le "Car".

J'en ai fait 2:

Car car1 = new Car();
Car car2 = new Car();

J'ai une fonction pour ajouter des éléments à ces objets Car:

car1.addPart("Front Wheels");
car1.addPart("Rear Wheels");
car1.addPart("Rear View Mirror");

car2.addPart("Rims");
car2.addPart("Steering Wheel");
car2.addPart("Bumper");

J'ai besoin d'une fonction appelée sameContents() que je peux appeler sur car1:

car1.sameContents(car2);

qui passe dans un objet de type ArrayList et le vérifie avec car1 pour voir s’ils ont le même contenu et dans le même ordre.

public boolean sameContents(Car c) {
    ArrayList<String> other_car = c; // error: Type mismatch: 
                                    // cannot convert from Car to ArrayList<String>

    for (String c : this.parts) {
        System.out.println(c);
        for(String oc : other_car) { 
             // stuff
        }
    }
}

Il me semble avoir toutes sortes de problèmes avec celui-ci. Je ne parviens pas à utiliser la variable other_car dans une boucle foreach.


Le deuxième qui doit être fait est transferContents.

Ça s'appelle comme:

car1.transferContents(car2); 

qui transfère les éléments de car2 dans car1 et laisse ensuite car2 vide. Je n'arrive pas à faire en sorte que la ArrayList fonctionne à nouveau dans une boucle foreach, ce dont je pense avoir besoin.

 public void transfer(Car c) {
     // code for transfer method.
     // this.parts is the arraylist of car parts
     for (Car c: c) {
    this.parts.add(c);
      }
    // not sure how to set car2 to empty...
 }
7
Drew Bartlett

Étant donné quelques List<T> foo, foreach boucles, par exemple:

for(T item : foo){
    // body
}

ne sont qu'une syntaxe abrégée pour cet idiome:

Iterator<T> iter = foo.iterator();
while(iter.hasNext()){
    T item = iter.next();
    // body
}

Pour vérifier qu'il y a plus d'éléments dans la liste, vous appelez iter.hasNext(), pour récupérer l'élément suivant, vous appelez iter.next().

Vous pouvez parcourir deux listes en conservant deux itérateurs, en vérifiant que les deux itérateurs ont plus d'éléments, puis en les récupérant. Nous pouvons éliminer certaines conditions aux limites sur des listes de longueurs différentes en réalisant que des listes de longueurs différentes ne peuvent pas contenir les mêmes éléments (car une liste en contient plus que l'autre).

D'après votre description, il semblerait que Car contient une propriété List<String> parts;. Nous pouvons donc formuler une solution comme suit:

// different sizes, can't be equal
if(this.parts.size() != other.parts.size()){
    return false;
}

// get iterators
Iterator<String> left = this.parts.iterator();
Iterator<String> right = other.parts.iterator();

// safe to only check `left` because the lists are the same size
while(left.hasNext()){
    // check if left part is equal to the right part
    if(!left.next().equals(right.next())){
        // values are different, know at this
        // point they're not equal
        return false;
    }
}

// at this point, have exactly the same values
// in the same order.
return true;

Pour ce qui est de votre méthode transferContents, vous avez la bonne idée, mais vous ne pouvez pas effectuer une itération sur la Car, vous devez effectuer une itération sur le List<String> parts. Pour supprimer des pièces individuelles, vous pouvez utiliser la méthode remove(), appelée méthode add, ou pour supprimer tous les éléments, vous pouvez appeler clear().

Mettre cela ensemble:

for (String part : c.parts) {
    this.parts.add(part);
}
c.parts.clear();
22
Mark Elliot

Vous pouvez compter sur l’API Java pour faire tout ce dont vous avez besoin. La méthode ArrayList equals vérifie l'ordre en comparant deux listes. Vous pouvez utiliser les méthodes removeAll () et addAll () pour transférer du contenu.

public class Car {

    private final List<String> parts = new ArrayList<String>();

    public void addPart(String p) {
        parts.add(p);
    }

    public boolean sameContents(Car c) {
        return this.parts.equals(c.parts);
    }

    public void transfer(Car c) {
        final List<String> temp = new ArrayList<String>(c.parts);
        temp.removeAll(this.parts);
        this.parts.addAll(temp);
        c.parts.clear();
    }
}
0
shams

Votre voiture ne devrait pas être une liste de tableaux, mais en avoir un. Par exemple. quelque chose comme ça:

class Car {
    ArrayList<String> parts;
    // ...
}

Ensuite, votre méthode sameContents peut simplement appeler la méthode .equals() des listes pour effectuer la comparaison:

public boolean sameParts(Car other) {
     return this.parts.equals(other.parts);
}

De même, pour transférer des pièces d'une autre voiture, utilisez les méthodes des listes pour add les pièces de votre liste, puis clear l'autre liste.

0
Paŭlo Ebermann