Comment puis-je convertir ArrayList <Object> en ArrayList <String>?

94
ArrayList<Object> list = new ArrayList<Object>();
list.add(1);
list.add("Java");
list.add(3.14);
System.out.println(list.toString());

J'ai essayé:

ArrayList<String> list2 = (String)list; 

Mais cela m'a donné une erreur de compilation.

rtf
la source
5
Pourquoi voulez-vous faire cela? Je veux dire, ce n'est pas sûr. Jetez un œil à l'exemple.
athspk
6
Vous mettez des non-chaînes dans la liste. Qu'attendez-vous de ce qui se passe si vous les forcez à être des cordes?
Ben Zotto
5
Je suppose que vous vouliez dire: ArrayList <String> list2 = (ArrayList <String>) liste;
Costi Ciudatu

Réponses:

130

Comme il ne s'agit en fait pas d'une liste de chaînes, le moyen le plus simple est de la boucler et de convertir vous-même chaque élément en une nouvelle liste de chaînes:

List<String> strings = list.stream()
   .map(object -> Objects.toString(object, null))
   .collect(Collectors.toList());

Ou lorsque vous n'êtes pas encore sur Java 8:

List<String> strings = new ArrayList<>(list.size());
for (Object object : list) {
    strings.add(Objects.toString(object, null));
}

Ou lorsque vous n'êtes pas encore sur Java 7:

List<String> strings = new ArrayList<String>(list.size());
for (Object object : list) {
    strings.add(object != null ? object.toString() : null);
}

Notez que vous devez déclarer par rapport à l'interface ( java.util.Listdans ce cas), pas à l'implémentation.

BalusC
la source
6
J'aime la façon dont les valeurs nulles sont conservées dans cette implémentation.
4
Si vous utilisez String.valueOf(object), vous n'aurez pas à faire la object != null ? object.toString() : nullchose
user219882
2
@Tomas: cela ajouterait une chaîne avec une valeur "null"au lieu du littéral null. Cela dépend en outre des exigences de l'entreprise, que ce soit souhaitable ou non. Pour moi, cela n'aurait pas du tout été acceptable car cela introduit un bug potentiellement majeur.
BalusC
1
@Tomas: "null"pas nulldu tout. Le nulla une signification particulière en Java. Cela n'a aucun sens d'être obligé de le faire if (item.equals("null"))lors de la vérification de cela par la suite.
BalusC
1
@Tomas: vous ne battez que la forte nature de frappe de Java de cette façon. Mais comme indiqué, cela dépend des exigences de l'entreprise si cela est souhaitable. Pour moi, c'est tout simplement inacceptable. Faites ce que vous voulez et le temps vous enseignera :)
BalusC
18

Ce n'est pas sûr de faire ça!
Imaginez si vous aviez:

ArrayList<Object> list = new ArrayList<Object>();
list.add(new Employee("Jonh"));
list.add(new Car("BMW","M3"));
list.add(new Chocolate("Twix"));

Cela n'aurait aucun sens de convertir la liste de ces objets en n'importe quel type.

athspk
la source
1
Sauf s'ils ont Object#toString()remplacé la méthode. Cependant, toute la conversion de type de X en String à d'autres fins que la présentation humaine n'a en effet pas beaucoup de sens.
BalusC
13

Si vous voulez le faire de manière sale, essayez ceci.

@SuppressWarnings("unchecked")
public ArrayList<String> convert(ArrayList<Object> a) {
   return (ArrayList) a;
}

Avantage: ici vous gagnez du temps en n'itérant pas sur tous les objets.

Inconvénient: peut produire un trou dans votre pied.

Par Lindberg
la source
12

Utilisation de la goyave :

List<String> stringList=Lists.transform(list,new Function<Object,String>(){
    @Override
    public String apply(Object arg0) {
        if(arg0!=null)
            return arg0.toString();
        else
            return "null";
    }
});
Emil
la source
11

En utilisant Java 8, vous pouvez faire:

List<Object> list = ...;
List<String> strList = list.stream()
                           .map( Object::toString )
                           .collect( Collectors.toList() );
Scadge
la source
10

Vous pouvez utiliser un caractère générique pour le faire comme suit

ArrayList<String> strList = (ArrayList<String>)(ArrayList<?>)(list);
Hellrocker
la source
8

Voici une autre alternative utilisant Guava

List<Object> lst ...    
List<String> ls = Lists.transform(lst, Functions.toStringFunction());
Husayt
la source
5

Votre code ArrayList<String> list2 = (String)list;ne se compile pas car il list2n'est pas de type String. Mais ce n'est pas le seul problème.

fastcodejava
la source
0

Utilisation de Java 8 lambda:

ArrayList<Object> obj = new ArrayList<>();
obj.add(1);
obj.add("Java");
obj.add(3.14);

ArrayList<String> list = new ArrayList<>();
obj.forEach((xx) -> list.add(String.valueOf(xx)));
Ankush soni
la source
0

Avec Java Generics Prend une liste de X et renvoie une liste de T qui étend ou implémente X, Sweet!

    // the cast is is actually checked via the method API
@SuppressWarnings("unchecked")
public static <T extends X, X> ArrayList<T> convertToClazz(ArrayList<X> from, Class<X> inClazz, Class<T> outClazz) {
    ArrayList<T> to = new ArrayList<T>();
    for (X data : from) {
        to.add((T) data);
    }
    return to;
}
Juste moi
la source
0

Une solution simple:

List<Object> lst  =listOfTypeObject;   
ArrayList<String> aryLst = new ArrayList<String>();
    for (int i = 0; i < lst.size(); i++) {
        aryLst.add(lst.get(i).toString());
    }

Remarque: cela fonctionne lorsque la liste contient tous les éléments du type de données String.

S Krishna
la source