java实现旅行商问题_旅行商问题

import java.io.IOException;

import java.nio.file.Files;

import java.nio.file.Paths;

import java.util.List;

import java.util.Random;

public class Test {

public static void main(String[] args) throws IOException {

List data = Files.readAllLines(Paths.get(

"test.file"));

Node[] nodes = new Node[102];

for (int i = 0; i < 102; i++) {

nodes[i] = new Node();

}

nodes[0].x = nodes[0].y = nodes[101].x = nodes[101].y = 0;

for (int i = 0; i < 100; i++) {

String point = data.get(i);

String[] xy = point.split(",");

nodes[i + 1].x = Integer.valueOf(xy[0]);

nodes[i + 1].y = Integer.valueOf(xy[1]);

}

//for (int i = 0; i < 101; i++) {

// int index = i + 1;

// int dist = 10000;

// for (int j = i + 1; j < 101; j++) {

// int d = countDist(nodes[i], nodes[j]);

// if (d < dist) {

// dist = d;

// index = j;

// }

// }

// Node k = nodes[index];

// nodes[index] = nodes[i + 1];

// nodes[i + 1] = k;

//}

System.out.println(getAnserString(nodes));

System.out.println("最优解:" + countCost(nodes, 1, 102));

int bestAnser = countCost(nodes, 1, 102);

long startTime = System.currentTimeMillis();

Random random = new Random();

while (true) {

if (System.currentTimeMillis() - startTime > 3 * 1000) {

break;

}

int p1 = random.nextInt(100);

int p2 = random.nextInt(100);

if (p1 == p2) {

continue;

}

Node k = nodes[p1 + 1];

Node h = nodes[p2 + 1];

nodes[p1 + 1] = h;

nodes[p2 + 1] = k;

int newAnser = countCost(nodes, 1, 102);

if (newAnser < bestAnser) {

System.out.println(getAnserString(nodes));

System.out.println("最优解:" + countCost(nodes, 1, 102));

bestAnser = newAnser;

} else {

nodes[p1 + 1] = k;

nodes[p2 + 1] = h;

}

}

System.out.println("--------------------------------------");

int minDist = countCost(nodes, 1, 102);

while (true) {

boolean flag = true;

for (int f = 10; f > 0; f--) {

System.out.println("--------------------继续----------------"+f);

for (int i = 1; i + maxDept <= 101; i += f) {

maxDist = 10000;

for (int j = 0; j < maxDept + 2; j++) {

indexNode[j] = position[j] = nodes[i + j - 1];

used[j] = false;

}

dfs(0, 0);

if(maxDist != 10000) {

for (int j = 0; j < maxDept; j++) {

nodes[j + i] = bestPosition[j];

}

}

if (minDist > countCost(nodes, 1, 102)) {

if (minDist > countCost(nodes, 1, 102)) {

System.out.println(getAnserString(nodes));

System.out.println("最优解:" + countCost(nodes, 1, 102));

minDist = countCost(nodes, 1, 102);

}

flag = false;

}

}

}

if (flag) {

break;

} else {

System.out.println("--------------------继续----------------");

}

}

}

final static int maxDept = 30;

public static Node[] bestPosition = new Node[maxDept + 2];

public static Node[] position = new Node[maxDept + 2];

public static Node[] indexNode = new Node[maxDept + 2];

public static boolean[] used = new boolean[maxDept + 2];

public static int maxDist = 100000;

public static void dfs(int depth, int countCost) {

if (depth == maxDept) {

int dist = countCost(position, 1, maxDept + 1);

if (dist < maxDist) {

maxDist = dist;

for (int i = 0; i < maxDept; i++) {

bestPosition[i] = position[i + 1];

}

}

return;

}

for (int i = 0; i < maxDept; i++) {

if (used[i]) {

continue;

}

int newCost = countCost + countDist(position[depth], indexNode[i + 1]);

if (newCost >= maxDist) {

continue;

}

used[i] = true;

position[depth + 1] = indexNode[i + 1];

dfs(depth + 1, newCost);

used[i] = false;

}

}

public static int countDist(Node a, Node b) {

return Math.abs(a.x - b.x) + Math.abs(a.y - b.y);

}

public static int countCost(Node[] nodes, int begin, int end) {

int anser = 0;

for (int i = begin; i < end; i++) {

anser += Math.abs(nodes[i].x - nodes[i - 1].x) + Math.abs(nodes[i].y - nodes[i - 1].y);

}

return anser;

}

public static String getAnserString(Node[] nodes) {

StringBuilder sb = new StringBuilder("0,0\n");

for (int i = 1; i <= 100; i++) {

sb.append(nodes[i].x).append(",").append(nodes[i].y).append("\n");

}

sb.append("0,0");

return sb.toString();

}

public static class Node {

public int x;

public int y;

}

}

0,8

1,9

14,8

24,6

35,2

36,7

37,8

38,6

47,4

60,4

67,0

67,10

66,13

82,14

82,17

83,18

90,19

94,13

94,21

98,25

88,28

81,29

84,36

71,36

66,49

53,55

54,68

53,69

49,71

43,75

36,78

36,87

40,88

40,93

50,98

38,97

32,90

27,87

25,88

23,92

17,89

10,91

8,94

13,82

2,76

5,73

9,65

8,62

10,60

14,57

25,56

24,53

19,50

13,47

11,41

4,42

8,38

20,31

29,25

29,24

36,23

33,19

33,15

40,15

48,33

49,37

43,41

42,43

34,44

26,44

19,64

22,71

30,72

38,73

55,82

58,78

60,79

69,81

69,69

77,69

77,65

80,57

94,48

95,48

96,50

98,53

98,61

98,62

94,62

96,77

95,97

92,95

90,94

91,91

83,87

83,86

73,98

69,97

64,91

41,51

旅行商问题

题目:起始点0,0,终止点0,0中间必须经过所有的点。求最短路径。

解法:

贪心求初始解,每次找最近的点走。

然后局部枚举所有路径求最优路径

本文地址:https://blog.csdn.net/firenet1/article/details/109236532

希望与广大网友互动??

点此进行留言吧!

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
蚁群算法是一种用于解决TSP问题的启发式算法,它模拟了蚂蚁在寻找食物时的行为,通过不断地迭代和信息素更新,最终找到一条较优的路径。以下是Java实现TSP旅行商问题的步骤: 1. 定义城市类City,包含城市的名称和坐标信息。 ```java public class City { private String name; private double x; private double y; //构造函数 public City(String name, double x, double y) { this.name = name; this.x = x; this.y = y; } //get方法 public String getName() { return name; } public double getX() { return x; } public double getY() { return y; } } ``` 2. 定义蚂蚁类Ant,包含蚂蚁的编号、当前所在城市、已访问城市列表、未访问城市列表、路径长度等信息。 ```java public class Ant { private int id; private City currentCity; private List<City> visitedCities; private List<City> unvisitedCities; private double pathLength; //构造函数 public Ant(int id, City startCity, List<City> cities) { this.id = id; this.currentCity = startCity; this.visitedCities = new ArrayList<>(); this.visitedCities.add(startCity); this.unvisitedCities = new ArrayList<>(cities); this.unvisitedCities.remove(startCity); this.pathLength = 0; } //get方法 public int getId() { return id; } public City getCurrentCity() { return currentCity; } public List<City> getVisitedCities() { return visitedCities; } public List<City> getUnvisitedCities() { return unvisitedCities; } public double getPathLength() { return pathLength; } //选择下一个城市 public City selectNextCity(double[][] pheromone, double alpha, double beta) { double[] probabilities = new double[unvisitedCities.size()]; double sum = 0; for (int i = 0; i < unvisitedCities.size(); i++) { City city = unvisitedCities.get(i); double pheromoneLevel = pheromone[currentCity.getName()][city.getName()]; double distance = getDistance(currentCity, city); probabilities[i] = Math.pow(pheromoneLevel, alpha) * Math.pow(1 / distance, beta); sum += probabilities[i]; } for (int i = 0; i < probabilities.length; i++) { probabilities[i] /= sum; } double random = Math.random(); double p = 0; for (int i = 0; i < probabilities.length; i++) { p += probabilities[i]; if (random < p) { City nextCity = unvisitedCities.get(i); visitedCities.add(nextCity); unvisitedCities.remove(nextCity); pathLength += getDistance(currentCity, nextCity); currentCity = nextCity; return nextCity; } } return null; } //计算两个城市之间的距离 private double getDistance(City city1, City city2) { double x1 = city1.getX(); double y1 = city1.getY(); double x2 = city2.getX(); double y2 = city2.getY(); return Math.sqrt(Math.pow(x1 - x2, 2) + Math.pow(y1 - y2, 2)); } } ``` 3. 定义蚁群类AntColony,包含城市列表、蚂蚁列表、信息素矩阵、信息素挥发率、信息素增强系数等信息。 ```java public class AntColony { private List<City> cities; private List<Ant> ants; private double[][] pheromone; private double evaporationRate; private double alpha; private double beta; private double Q; //构造函数 public AntColony(List<City> cities, int antCount, double evaporationRate, double alpha, double beta, double Q) { this.cities = cities; this.ants = new ArrayList<>(); for (int i = 0; i < antCount; i++) { Ant ant = new Ant(i, cities.get(0), cities); ants.add(ant); } this.pheromone = new double[cities.size()][cities.size()]; for (int i = 0; i < cities.size(); i++) { for (int j = 0; j < cities.size(); j++) { pheromone[i][j] = 1; } } this.evaporationRate = evaporationRate; this.alpha = alpha; this.beta = beta; this.Q = Q; } //运行蚁群算法 public List<City> run(int maxIterations) { List<City> bestTour = null; double bestLength = Double.MAX_VALUE; for (int i = 0; i < maxIterations; i++) { for (Ant ant : ants) { while (!ant.getUnvisitedCities().isEmpty()) { ant.selectNextCity(pheromone, alpha, beta); } ant.getPathLength() += getDistance(ant.getCurrentCity(), ant.getVisitedCities().get(0)); if (ant.getPathLength() < bestLength) { bestLength = ant.getPathLength(); bestTour = new ArrayList<>(ant.getVisitedCities()); } for (int j = 0; j < ant.getVisitedCities().size() - 1; j++) { int city1 = ant.getVisitedCities().get(j).getName(); int city2 = ant.getVisitedCities().get(j + 1).getName(); pheromone[city1][city2] = (1 - evaporationRate) * pheromone[city1][city2] + evaporationRate * Q / ant.getPathLength(); pheromone[city2][city1] = pheromone[city1][city2]; } ant.getVisitedCities().clear(); ant.getVisitedCities().add(cities.get(0)); ant.getUnvisitedCities().clear(); ant.getUnvisitedCities().addAll(cities); ant.getUnvisitedCities().remove(cities.get(0)); ant.setPathLength(0); } } return bestTour; } //计算两个城市之间的距离 private double getDistance(City city1, City city2) { double x1 = city1.getX(); double y1 = city1.getY(); double x2 = city2.getX(); double y2 = city2.getY(); return Math.sqrt(Math.pow(x1 - x2, 2) + Math.pow(y1 - y2, 2)); } } ``` 4. 在主函数中读取城市信息,创建AntColony对象并运行蚁群算法,输出最优路径和路径长度。 ```java public static void main(String[] args) { List<City> cities = new ArrayList<>(); try { BufferedReader reader = new BufferedReader(new FileReader("cities.txt")); String line; while ((line = reader.readLine()) != null) { String[] parts = line.split(","); String name = parts[0]; double x = Double.parseDouble(parts[1]); double y = Double.parseDouble(parts[2]); City city = new City(name, x, y); cities.add(city); } reader.close(); } catch (IOException e) { e.printStackTrace(); } AntColony antColony = new AntColony(cities, 50, 0.5, 1, 5, 100); List<City> bestTour = antColony.run(1000); System.out.println("Best tour: " + bestTour); double bestLength = 0; for (int i = 0; i < bestTour.size() - 1; i++) { bestLength += antColony.getDistance(bestTour.get(i), bestTour.get(i + 1)); } System.out.println("Best length: " + bestLength); } ```

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值