同步传递的ArrayList

时间:2017-05-24 19:18:14

标签: java multithreading swing arraylist

我有一个项目包含一些JFrames和小点移动并模拟生物。这些应该能够重现和死亡,因此我需要修改所有生物的ArrayList。

我读了一些关于同步的事情,虽然我没有真正得到以下内容: 我知道您可以在创建时创建同步方法或变量。 ArrayList在单独的JFrame中创建并传递给" World "类。

有一个课程" 操作"它处理所有动作,如死和重现,我也传递ArrayList进行修改。

此类名为" 工具包"它处理诸如起始人口等事情。" 世界"包含一个重新绘制生物的线程,并让它们移动每个刻度。

此外还有一个课程" 画笔"它处理图形内容并扩展另一个JFrame以显示Graphic.drawStrings,这个类也获取ArrayList来显示死亡的生物。

那么如何以及在哪里创建同步以在进行刻度时更改列表? 如果你要求代码我将使用指定的代码更新我的问题,这些类非常庞大和混乱。 谢谢你帮助^^

简化示例:

工具包:

public static ArrayList<Creature> generateCreatures() {
    int amount_creatures = 10;
    ArrayList<Creature> all = new ArrayList<>();
        for(int i = 0; i < amount_creatures; i++) {
            Creature creature = new Creature(id, sex, age, energy);
            all.add(creature);
        }
    }
    return all;

世界:

public World(ArrayList<Creature> all ...) {
    this.all = all;
        ...
    startAnimation();
} 
private void startAnimation() {
        Toolkit.progress("Start Animation");
        startDrawThread();
        new Thread() {
            public void run() {
                Toolkit.step("Animation Thread started");
                try {
                    int warten;
                    long last = System.currentTimeMillis(), latest;
                    int ticks_ps = World.this.ticks_ps;
                    Toolkit.step("Ticks PS : " + ticks_ps);
                    float millsStepInterval = 1000f / ticks_ps;
                    int i = 1;

                    actions = new Actions(paint, World.this);

                    for (steps = 0; steps < Integer.MAX_VALUE - ticks_ps && running; steps++) {

                        nextTick();

                        latest = System.currentTimeMillis();
                        warten = Math.max(Math.round(millsStepInterval * i + (last - latest)), 0);

                        if (i == ACCURACY) {
                            i = 1;
                            last = latest + warten;
                        } else
                            i++;
                        Thread.sleep(warten);

                        synchronized (World.this) {
                            if (ticks_ps != World.this.ticks_ps) {
                                ticks_ps = World.this.ticks_ps;
                                millsStepInterval = 1000f / ticks_ps;
                            }
                        }
                    }
                } catch (InterruptedException e) {
                    e.printStackTrace();
                    interrupt();
                }
                Toolkit.step("Animation Thread finished");
            }
        }.start();

    }


private void nextTick() throws InterruptedException {

        for (Creature creature : all) {

            double moveratio = (double) (Math.random() * creature.getAge() / 100);


            if(moveratio < 5) {
                actions.move(all, creature, size.x, size.y);
            }
            else {
                actions.idle();
            }


            creature.setAge(creature.getAge() + 1);

            for(Creature creature1 : all) {
                for(Creature creature2 : all) {
                    if(Toolkit.isNextTo(creature1, creature2)){
                        if (creature1.getSex() != creature2.getSex()) {
                            if(creature1.getAge() > 1000 && creature2.getAge() > 1000) {
                                Creature mother = null;
                                if (creature1.getSex() == 1) {
                                    mother = creature1;
                                } else if (creature2.getSex() == 1) {
                                    mother = creature2;
                                }
                                actions.reproduce(mother, all);
                            }
                        }

                    }
                }
            }


        }

操作:

public static void reproduce(Creature creature, ArrayList<Creature> all) {
        int id = Toolkit.getID(all);
        Creature baby = new Creature(id, energy, creature.getPosition(), 2, Toolkit.generateSex(), creature.getSize());
        all.add(baby);
    }

漆:

public Paint(World world, ArrayList<Creature> all) {
        super();
        this.world = world;
        this.all = all;
        setBackground(Color.WHITE);
        deads = new boolean[all.size()]; //<-- THIS ONE HAS TO BE UPDATED EACH TIME THE LIST CHANGES
    }

1 个答案:

答案 0 :(得分:1)

您可以使用提供方法storeItem = JSON.parse(storage.getItem('domehaProducts')); let cart = order.items.map(item => { const storeobj = storeItem.products.find(prod => prod.id == item.id); return Object.assign(item, { images: storeobj.image, name: storeobj.name, price: storeobj.display_price, intPrice: storeobj.price}); }); 的课程Colections(请参阅此处的API)。您也可以使用类public static <T> List<T> synchronizedList(List<T> list)这是一个同步的ArrayList,但这是非常古老的方式。但在你做任何关于并发问题的阅读之前,要了解你是否真的需要这样做,因为同步是一种非常广泛的奢侈。你有不同的线程同时改变你的列表吗?看看你是否真的需要它。