programming-examples/java/Data_Structures/MisWeighted.java

63 lines
1.7 KiB
Java
Raw Normal View History

2019-11-15 12:59:38 +01:00
import java.util.*;
public class MisWeighted {
public static int mis(long[] g, long unused, int[] weights) {
if (unused == 0)
return 0;
int v = -1;
for (int u = Long.numberOfTrailingZeros(unused); u < g.length; u += Long.numberOfTrailingZeros(unused >> (u + 1)) + 1)
if (v == -1 || Long.bitCount(g[v] & unused) > Long.bitCount(g[u] & unused))
v = u;
int res = 0;
long nv = g[v] & unused;
for (int y = Long.numberOfTrailingZeros(nv); y < g.length; y += Long.numberOfTrailingZeros(nv >> (y + 1)) + 1)
res = Math.max(res, weights[y] + mis(g, unused & ~g[y], weights));
return res;
}
// random test
public static void main(String[] args) {
Random rnd = new Random(1);
for (int step = 0; step < 1000; step++) {
int n = rnd.nextInt(16) + 1;
long[] g = new long[n];
int[] weights = new int[n];
for (int i = 0; i < n; i++) {
weights[i] = rnd.nextInt(1000);
// for convenience of mis()
g[i] |= 1L << i;
}
for (int i = 0; i < n; i++)
for (int j = 0; j < i; j++)
if (rnd.nextBoolean()) {
g[i] |= 1L << j;
g[j] |= 1L << i;
}
int res1 = mis(g, (1L << n) - 1, weights);
int res2 = misSlow(g, weights);
if (res1 != res2)
throw new RuntimeException();
}
}
static int misSlow(long[] g, int[] weights) {
int res = 0;
int n = g.length;
for (int set = 0; set < 1 << n; set++) {
boolean ok = true;
for (int i = 0; i < n; i++)
for (int j = 0; j < i; j++)
ok &= (set & (1 << i)) == 0 || (set & (1 << j)) == 0 || (g[i] & (1L << j)) == 0;
if (ok) {
int cur = 0;
for (int i = 0; i < n; i++)
if ((set & (1 << i)) != 0)
cur += weights[i];
res = Math.max(res, cur);
}
}
return res;
}
}