Распечатать все элементы Arraylist типа List/String

53
5

Мне нужно напечатать каждый элемент ArrayList. Этот ArrayList может иметь тип ArrayList или String. Другие потомки этого списка также могут быть списком типов.

Вот что я написал до сих пор:

public class Logic extends AppCompatActivity {

ArrayList<Object> parent = new ArrayList<>();
ArrayList<Object> check = new ArrayList<>();

@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);

parent.add("list 1");
check.add("list 2");
check.add(parent);
parent.add(check);

for (int i = 0; i < parent.size(); i++) {
if (!(parent.get(i) instanceof ArrayList)) {
Log.e("test",(String) parent.get(i));
} else {
printDetails((ArrayList<?>) parent.get(i));
}
}
}

public synchronized void printDetails(ArrayList<?> child) {
for (int i = 0; i < child.size(); i++) {
if (!(child.get(i) instanceof ArrayList)) {
Log.e("test1", (String) child.get(i));
} else {
printDetails((ArrayList<?>) child.get(i));
}
}
}
}

Но это печатает все резкие значения без ожидаемого порядка. Ожидается, что все значения должны печататься последовательно. Например, если первый элемент списка является строкой, он должен сначала напечатать строку, если это список, если вывести все значения этого дочернего списка, и если какой-либо элемент дочернего списка снова окажется в списке, он должен также напечатать эти значения и переместить вернуться к следующему элементу родительского списка.

Если это вход:

ArrayList<Object> parent = new ArrayList<>();
ArrayList<Object> child1 = new ArrayList<>();
ArrayList<Object> subChild1= new ArrayList<>();
ArrayList<Object> nestedSubChild1= new ArrayList<>();

parent.add("list 1");
parent.add("list 1-2");

child1.add("childlist 2");
subChild1.add("sublist 1-1");
subChild1.add("sublist 1-2");
nestedSubChild1.add("nestedlist 1-1");
nestedSubChild1.add("nestedlist 1-2");
subChild1.add(nestedSubChild1);
child1.add(subChild1);
parent.add(child1);

Я хочу этот вывод

list 1
list 1-2
childlist 2
sublist 1-1
sublist 1-2
nestedlist 1-1
nestedlist 1-2

Другим требованием является использование рекурсии, чтобы код был эффективным.

спросил(а) 2018-12-17T11:28:00+03:00 1 год, 5 месяцев назад
1
Решение
54

Вы можете сделать это, создав рекурсивный метод для печати списков

public static void printRecursiveList(List myList) {
for (Object obj : myList) {
if (obj instanceof List) {
printRecursiveList((List) obj); // call itself again since its a list
} else {
System.out.println(obj);
}
}
}

Теперь вы можете позвонить, используя:

parent.stream().forEach(i -> {
if (i instanceof List) {
printRecursiveList((List) i);
} else {
System.out.println(i);
}
});

Здесь мы перемещаемся по parent списку и, если элемент является экземпляром списка, мы вызываем printRecursiveList(...) иначе мы распечатываем элемент.

ответил(а) 2018-12-17T12:17:00+03:00 1 год, 5 месяцев назад
37

Попробуй это. Он должен работать.

import java.util.ArrayList;

public class PrintArrayList
{
public static void main(String[] args)
{
ArrayList<Object> parent = new ArrayList<>();
ArrayList<Object> child1 = new ArrayList<>();
ArrayList<Object> subChild1= new ArrayList<>();
ArrayList<Object> nestedSubChild1= new ArrayList<>();

parent.add("list 1");
parent.add("list 1-2");

child1.add("childlist 2");
subChild1.add("sublist 1-1");
subChild1.add("sublist 1-2");
nestedSubChild1.add("nestedlist 1-1");
nestedSubChild1.add("nestedlist 1-2");
subChild1.add(nestedSubChild1);
child1.add(subChild1);
parent.add(child1);

print(parent);
}

public static void print(ArrayList<Object> arrayList)
{
for (Object element : arrayList)
{
if (element instanceof ArrayList)
{
print((ArrayList) element);
}
else
{
System.out.println(element);
}
}
}
}

ответил(а) 2018-12-17T12:25:00+03:00 1 год, 5 месяцев назад
38

Я проверил ваш код со статическими переменными, он компилируется, как вы ожидали. Увидеть ниже:

import java.util.ArrayList;
import java.util.*;
public class MyClass {
static ArrayList<Object> parent = new ArrayList<>();
static ArrayList<Object> check = new ArrayList<>();
static ArrayList<Object> check2 = new ArrayList<>();

public static void main(String args[]) {

parent.add("list 1");
parent.add("list 2");
check.add("list 3");
check2.add("list 4");
check2.add("list 5");
check2.add("list 6");
check.add(check2);
//check.add(parent);
parent.add(check);

System.out.println(Arrays.deepToString(parent.toArray()));
System.out.println("-------");
for (int i = 0; i < parent.size(); i++) {
if (!(parent.get(i) instanceof ArrayList)) {
System.out.println("firstPart -> " + (String) parent.get(i));
}
else {
printDetails((ArrayList<?>) parent.get(i));
}
}
}
public static void printDetails(ArrayList<?> child) {
for (int i = 0; i < child.size(); i++) {
if (!(child.get(i) instanceof ArrayList)) {
System.out.println("lastPart -> " + (String) child.get(i));
} else {
printDetails((ArrayList<?>) child.get(i));
}
}
}
}

Но я обнаружил, что когда я раскомментирую закомментированный блок "check.add(parent);", он создает вложенный цикл, который генерирует java.lang.StackOverflowError.

Кстати, вы можете использовать

Arrays.deepToString(parent.toArray());

метод, если вы только регистрируете значения в порядке.

ответил(а) 2018-12-17T11:54:00+03:00 1 год, 5 месяцев назад
37

Вы можете распечатать необходимые элементы класса Model, переопределив метод toString() объекта.
Поддержка Вы получили и ArrayList из Child класса, то есть ArrayList<Child>:
- toString() может быть реализовано так:

class Child {

private String name;
.... some other variable

@Override
public String toString() {
return "Name: " + name + ": last updated: " +lastUpdated;
}
}

Теперь, когда вы печатаете child.toString(), результат будет напечатан так, как вы хотите его напечатать.

ответил(а) 2018-12-17T11:37:00+03:00 1 год, 5 месяцев назад
Ваш ответ
Введите минимум 50 символов
Чтобы , пожалуйста,
Выберите тему жалобы:

Другая проблема