2

请我英语不好,并且是编程初学者,所以请耐心等待。

请先查看我的代码,以便您更好地了解我遇到的问题。

我创建了一个名为ObjAbc.java

package exer;

public class ObjAbc {
    private Integer code;
    private Integer value;

    public ObjAbc () {

    }

    public ObjAbc (Integer code, Integer value) {
            this.code = code;
            this.value = value;
    }

    public Integer getCode() {
            return code;
    }

    public void setCode(Integer code) {
            this.code = code;
    }

    public Integer getValue() {
            return value;
    }

    public void setValue(Integer value) {
            this.value = value;
    }

    @Override
    public String toString() {
           return "ObjAbc [code=" + code + ", value=" + value + "]";
    }
}

然后我有课ObjAbcTest.java

package exer;

import java.util.ArrayList;
import java.util.List;

public class ObjAbcTest {

    public static List<ObjAbc> populateList() {
        List<ObjAbc> objAbcs = new ArrayList<ObjAbc>();
        objAbcs.add(new ObjAbc(1, 11));
        objAbcs.add(new ObjAbc(2, 25));
        objAbcs.add(new ObjAbc(3, 125));
        objAbcs.add(new ObjAbc(4, 73));
        objAbcs.add(new ObjAbc(5, 12));
        objAbcs.add(new ObjAbc(1, 12));
        objAbcs.add(new ObjAbc(3, 1));
        return objAbcs;
    }

    public static void main(String[] args) {
        List<ObjAbc> list = populateList();
        List<ObjAbc> newList = new ArrayList<ObjAbc>();
        for (ObjAbc o : list) {
            if (!newList.isEmpty()) {
                for (ObjAbc n : newList) {
                    if (o.getCode().intValue() == n.getCode().intValue()) {
                        n.setValue(n.getValue() + o.getValue());
                        break;
                    } 
                    else {
                        newList.add(o);
                    }
                }
            } 
            else {
                newList.add(o);
            }
        }

        for (ObjAbc n : newList) 
            System.out.println(n.toString());
    }
}

我试图做的是将所有ObjAbc具有相同代码的所有值相加,但在ObjAbc对值求和后删除另一个,这意味着对象必须显示一次,但值应该是总数。

例子:

输入:

ObjAbc [code=1, value=11]
ObjAbc [code=2, value=25]
ObjAbc [code=3, value=125]
ObjAbc [code=4, value=73]
ObjAbc [code=5, value=12]
ObjAbc [code=1, value=12]
ObjAbc [code=3, value=1]

预期输出:

ObjAbc [code=1, value=23]
ObjAbc [code=2, value=25]
ObjAbc [code=3, value=126]
ObjAbc [code=4, value=73]
ObjAbc [code=5, value=12]

但我得到的是:

Exception in thread "main" java.util.ConcurrentModificationException
    at java.util.AbstractList$Itr.checkForComodification(AbstractList.java:372)
    at java.util.AbstractList$Itr.next(AbstractList.java:343)
    at exer.ObjAbcTest.main(ObjAbcTest.java:25)
4

5 回答 5

2

这应该有效(未经测试)。

public class ObjAbcTest {

    public static List<ObjAbc> populateList() {
            // same as yours
    }

    public static void main(final String[] args) {
        final List<ObjAbc> list = populateList();
        final Map<Integer, Integer> sums = new HashMap<Integer, Integer>();

        // compute sums
        for (final ObjAbc obj: list) {
            // this if can be simplified with ? operator
            if (sums.containsKey(obj.getCode())) {
                sums.put(obj.getCode(), sums.get(obj.getCode()) + obj.getValue());
            } else {
                sums.put(obj.getCode(), obj.getValue());
            }
        }

        // populates newList
        final List<ObjAbc> newList = new ArrayList<ObjAbc>();
        for (final Map.Entry<Integer, Integer> e : sums.entrySet()) {
            newList.add(new ObjAbc(e.getKey(), e.getValue()));
        }

        // TODO: sort?

        // outputs
        for (final ObjAbc n : newList) 
            System.out.println(n.toString());
        }
}

在这里,我们使用Map(code => sum) 来存储总和。

于 2013-09-23T05:14:05.997 回答
1

You're modifying newList via

 newList.add() 

while iterating on the list:

 for (ObjAbc n : newList)

Which invalidates the iterator.

You could, for instance, use ListIterator, which allows you to modify the list while iterating. E.g.:

 ListIterator<ObjAbc> li = newList.listIterator();
 while (li.hasNext()) {
    ObjAbc n = li.next();
    if (...) 
    else {
      li.add(...)
    }
 }
于 2013-09-23T05:07:08.570 回答
0

for each loop in Java uses an implicit iterator. And ArrayList's iterator is fail-fast by design. It throws a ConcurrentModificationException as soon as it detects change in underlying structure (list).

Basically, the list has "modified" now and the iterator corresponds to list's previous state. Runtime detects this and throws exception.

Read here on how to handle such cases.

于 2013-09-23T05:07:10.490 回答
0
newList.add(o);

While iterating over collection you cannot modify it.

That is the issue while adding.

What you can do is simply take another list and add items to it.

于 2013-09-23T05:07:36.673 回答
0

我修复了您的代码,问题在于第二个循环中的 add 不正确,因为如果新值与newList.

这应该工作:包exer;

import java.util.ArrayList;
import java.util.List;

public class ObjAbcTest {

    public static List<ObjAbc> populateList() {
        List<ObjAbc> objAbcs = new ArrayList<ObjAbc>();
        objAbcs.add(new ObjAbc(1, 11));
        objAbcs.add(new ObjAbc(2, 25));
        objAbcs.add(new ObjAbc(3, 125));
        objAbcs.add(new ObjAbc(4, 73));
        objAbcs.add(new ObjAbc(5, 12));
        objAbcs.add(new ObjAbc(1, 12));
        objAbcs.add(new ObjAbc(3, 1));
        return objAbcs;
    }

    public static void main(String[] args) {
        List<ObjAbc> list = populateList();
        List<ObjAbc> newList = new ArrayList<ObjAbc>();
        for (ObjAbc o : list) {
            if (!newList.isEmpty()) {
                boolean found = false;
                for (ObjAbc n : newList) {
                    if (o.getCode().intValue() == n.getCode().intValue()) {
                        n.setValue(n.getValue() + o.getValue());
                        found = true;
                    } 
                }
                if (!found) {
                    newList.add(o);
                }
            } 
            else {
                newList.add(o);
            }
        }

        for (ObjAbc n : newList) 
            System.out.println(n.toString());
    }
}
于 2013-09-23T05:35:31.300 回答