题目描述:
给定一个无向图graph,当这个图为二分图时返回true。
如果我们能将一个图的节点集合分割成两个独立的子集A和B,并使图中的每一条边的两个节点一个来自A集合,一个来自B集合,我们就将这个图称为二分图。
graph将会以邻接表方式给出,graph[i]表示图中与节点i相连的所有节点。每个节点都是一个在0到graph.length-1之间的整数。这图中没有自环和平行边: graph[i] 中不存在i,并且graph[i]中没有重复的值。
【注意:有很多孤立点!!!!】
今日学习:
1.染色法判断二分图
题解:
1.没想到用dfs,失败了
2.dfs,给v染色,判断与v邻接的w:染色?false?
/**
* @param {number[][]} graph
* @return {boolean}
*/
/*var isBipartite = function(graph) {
let n = graph.length
//0代表黑色,1代表白色,2代表未染色
const color = new Array(n).fill(2)
color[0] = 0
for(let i = 0; i < n; i++) {
if(color[i] == 2) {
for(let j = 0; j < graph[i].length; j++) {
if(color[i] == 2 && color[graph[i][j]] != 2) {
color[i] = color[graph[i][j]] == 0 ? 1 : 0
}else if(color[i] != 2 && color[graph[i][j]] != 2) {
if(color[i] == color[graph[i][j]]) {
return false
}
}
}
if(color[i] == 2) {
color[i] = 0
}
}
for(let j = 0; j < graph[i].length; j++) {
if(color[graph[i][j]] == 2) {
color[graph[i][j]] = color[i] == 0 ? 1 : 0
}else if(color[graph[i][j]] == color[i]) {
return false
}
}
}
return true
};*/
var isBipartite = function(graph) {
//点的个数
let n = graph.length
//空图返回true
if(n == 1 && graph[0].length == 0) return true
//点的颜色
const colors = new Array(n)
//是否染过色
const marked = new Array(n).fill(false)
//点0先染色
colors[0] = true
//dfs:标记当前点,给没染色的邻接点染色,进入该点继续dfs;判断染过色的邻接点颜色是否相同
var dfs = function(v, G) {
marked[v] = true
for(let j in G[v]){
let w = G[v][j]
if(!marked[w]){
colors[w] = !colors[v]
if(!dfs(w,G)) {
return false
}
}else if(colors[w] == colors[v]){
return false
}
}
return true
}
for(let i = 0; i < n; i++){
if(marked[i] == false){
if(graph[i].length != 0) {
if(!dfs(i, graph)){
return false
}
}
}
}
return true
}