有缺陷的2-opt搜索实施?

时间:2012-12-04 02:27:30

标签: java heuristics traveling-salesman

我正在尝试为Java中的TSP设计2-opt本地搜索启发式算法,但我的算法似乎存在缺陷。给定输入中的最近邻电路,它会以某种方式使电路变得更糟。最近的邻居:http://goo.gl/uI5X6;经过10秒的2-opt:http://goo.gl/5AGJ1。我的代码如下。我的实施有什么问题?位置[]位置只是“图形”节点的列表,每个节点都有纬度和经度以及它与另一个节点之间的距离计算。

    public HamiltonianCircuit execute(Location[] locations) {
    long startTime = System.currentTimeMillis();
    while (true) {
        for (int i = 0; i < locations.length; i++) {
            for (int k = 0; k < locations.length; k++) {
                if (System.currentTimeMillis() - startTime >= 10000) {
                    return new HamiltonianCircuit(locations);
                }
                Location a = locations[i];
                Location b = locations[(i + 1) % locations.length];
                Location c = locations[k];
                Location d = locations[(k + 1) % locations.length];
                double distanceab = a.distanceBetween(b);
                double distancecd = c.distanceBetween(d);
                double distanceac = a.distanceBetween(c);
                double distancebd = b.distanceBetween(d);
                double change = (distanceab + distancecd) - 
                    (distanceac + distancebd);
                if (change > 0) {
                    locations[k] = a;
                    locations[i] = c;
                }
            }
        }
    }
}

2 个答案:

答案 0 :(得分:1)

2-opt正在用边缘AC和BD替换AB和CD边缘,这意味着如果我们要开始使用部分电路0 AB xyz CD 1,我们在完成时需要0 AC zyx BD 1。登记/> 您的代码将生成0 C B x y z A D 1.

您想要交换B和C,但也需要在中间反转所有内容。

答案 1 :(得分:-2)

Java中可能的解决方案可能是:(注:详细)

public HamiltonianCircuit execute(){
ArrayList<Vehicle> locations= new ArrayList<Locations>;
//populate array

    for (int i = 1; i < locations.size()-3; i++) {
            Location a = locations.get(i);
            Location b = locations.get(i+1);
            Location c = locations.get(i+2);
            Location d = locations.get(i+3);

            double distanceab = EuclidianDistance.pair(a, b);
            double distancebd = EuclidianDistance.pair(b, d);
            double distanceac = EuclidianDistance.pair(a, c);
            double distancecd = EuclidianDistance.pair(c, d);
            double abcd = distanceab+distancecd;
            double acbd = distanceac+distancebd;

            if(acbd<abcd){
                Collections.swap(locations, i+1, i+2);
                System.out.println("swapped"+vehicles);
            }
    }
    Locations.setDistance(EuclidianDistance.Collection(locations));
    return locations;
}