把相邻顶点染成不同颜色的问题叫做图的着色问题。
对图进行染色所需的最小颜色数,称为最小着色数。
最小着色数为2的图称为二分图。
给定一个具有n个顶点的图,要给图上每个顶点染色,并且要使相邻的顶点的颜色不同、问能否最多用2种颜色进行染色?没有重边和自环。
参考代码:
import java.util.ArrayList;
import java.util.List;
//邻接表
class GraphNode {
public int val;
private List<GraphNode> neighbors;//邻居
public boolean checked = false;
public GraphNode(int val) {
this.val = val;
}
public GraphNode getNeighbor(int i) {
return neighbors.get(i);
}
public void add(GraphNode node) {
if (this.neighbors == null)
this.neighbors = new ArrayList<>();
this.neighbors.add(node);
}
public int size() {
return this.neighbors.size();
}
}
class MyNode extends GraphNode {
int color;
public MyNode(int val) {
super(val);
}
public MyNode(int val, int color) {
super(val);
this.color = color;
}
}
public class Main {
public static void main(String[] args) {
MyNode n1 = new MyNode(1);
MyNode n2 = new MyNode(2);
MyNode n3 = new MyNode(3);
MyNode n4 = new MyNode(4);
n1.add(n2);
n1.add(n4);
n2.add(n1);
n2.add(n3);
n3.add(n2);
n3.add(n4);
n4.add(n1);
n4.add(n3);
//从节点n1开始着色(其实可以从任意顶点开始着色)
System.out.println(dfs(n1, 1));
}
private static boolean dfs(MyNode node, int c) {
//color同时具有是否被访问、代表具体颜色的功能(两种颜色设为c和-c)
node.color = c;
//遍历所有相邻顶点
for (int i = 0; i < node.size(); ++i) {
//具体的相邻顶点
MyNode neighbor = (MyNode) node.getNeighbor(i);
//如果相邻节点颜色一样,返回false
if (neighbor.color == c) {
return false;
}
//如果没有被染色,就染不同颜色(-c)进行递归
if (neighbor.color == 0) {
boolean res = dfs(neighbor, -c);
//从当前节点开始染色无法形成二分图,就返回false
if (!res) {
return false;
}
}
}
//从当前节点开始染色,能形成二分图
return true;
}
}