dkl9 commited on 2025-186 01:56:15
Showing 1 changed files, with 31 additions and 4 deletions.
| ... | ... |
@@ -59,17 +59,25 @@ def show_mat(distances: DistTable) -> str: |
| 59 | 59 |
rows.append(row) |
| 60 | 60 |
return "\n".join(rows) |
| 61 | 61 |
|
| 62 |
+# promising |
|
| 62 | 63 |
def score_nearest(distances: DistTable, sample: IndSeq) -> float: |
| 63 |
- return sum(min(distances[i][j] for j in sample) for i in range(len(distances))) |
|
| 64 |
+ return sum(0 if i in sample else min(distances[i][j] for j in sample) for i in range(len(distances))) |
|
| 64 | 65 |
|
| 66 |
+# too centred and slow |
|
| 65 | 67 |
def score_total(distances: DistTable, sample: IndSeq) -> float: |
| 66 | 68 |
return sum(sum( |
| 67 | 69 |
0 if i in sample else distances[i][j] for j in sample |
| 68 | 70 |
) for i in range(len(distances))) |
| 69 | 71 |
|
| 72 |
+# promising, needs revision |
|
| 70 | 73 |
def score_spread(distances: DistTable, sample: IndSeq) -> float: |
| 71 | 74 |
return -sum(sum(distances[sample[i]][j] for j in sample[:i]) for i in range(len(sample))) |
| 72 | 75 |
|
| 76 |
+def score_sqrt_spread(distances: DistTable, sample: IndSeq) -> float: |
|
| 77 |
+ return -sum(sum( |
|
| 78 |
+ math.sqrt(distances[sample[i]][j]) for j in sample[:i] |
|
| 79 |
+ ) for i in range(len(sample))) |
|
| 80 |
+ |
|
| 73 | 81 |
def greedy_min_seq(distances: DistTable, score_func: Func[[DistTable, IndSeq], float]) -> IndSeq: |
| 74 | 82 |
seq = [] |
| 75 | 83 |
options = set(range(len(distances))) |
| ... | ... |
@@ -79,6 +87,23 @@ def greedy_min_seq(distances: DistTable, score_func: Func[[DistTable, IndSeq], f |
| 79 | 87 |
options.remove(best) |
| 80 | 88 |
return seq |
| 81 | 89 |
|
| 90 |
+def score_maximin(distances: DistTable, sample: IndSeq) -> float: |
|
| 91 |
+ return min(min(distances[sample[i]][j] for j in sample[:i]) for i in range(1, len(sample))) |
|
| 92 |
+ |
|
| 93 |
+# promising |
|
| 94 |
+def greedy_maximin(distances: DistTable) -> IndSeq: |
|
| 95 |
+ seq = [] |
|
| 96 |
+ options = set(range(len(distances))) |
|
| 97 |
+ start = min(options, key=lambda o: score_nearest(distances, [o])) |
|
| 98 |
+ seq.append(start) |
|
| 99 |
+ options.remove(start) |
|
| 100 |
+ while options: |
|
| 101 |
+ best = max(options, key=lambda o: score_maximin(distances, seq + [o])) |
|
| 102 |
+ seq.append(best) |
|
| 103 |
+ options.remove(best) |
|
| 104 |
+ return seq |
|
| 105 |
+ |
|
| 106 |
+# too edge-clustery |
|
| 82 | 107 |
def furthest_nb(distances: DistTable) -> IndSeq: |
| 83 | 108 |
seq = [] |
| 84 | 109 |
options = set(range(len(distances))) |
| ... | ... |
@@ -103,6 +128,7 @@ def distance_hierarchy(distances: DistTable) -> BinaryTree: |
| 103 | 128 |
p = forest[i].merge(forest[j]) |
| 104 | 129 |
return p |
| 105 | 130 |
|
| 131 |
+# promising |
|
| 106 | 132 |
def scattered_hierarchy(hierarchy: BinaryTree) -> IndSeq: |
| 107 | 133 |
seq = [] |
| 108 | 134 |
while hierarchy.usage < hierarchy.weight: |
| ... | ... |
@@ -131,14 +157,15 @@ t.hideturtle() |
| 131 | 157 |
t.pen(speed=10) |
| 132 | 158 |
dt: DistTable = distance_table(points, math.dist) |
| 133 | 159 |
print(show_mat(dt)) |
| 160 |
+to = time.time() |
|
| 134 | 161 |
h: BinaryTree = distance_hierarchy(dt) |
| 162 |
+tf = time.time() |
|
| 163 |
+print(f"took {tf - to} s to build hierarchy")
|
|
| 135 | 164 |
print(h) |
| 136 | 165 |
METHODS = [ |
| 137 | 166 |
("graph", lambda: scattered_hierarchy(h)),
|
| 138 | 167 |
("nearest-nb sum", lambda: greedy_min_seq(dt, score_nearest)),
|
| 139 |
- ("all dist sum", lambda: greedy_min_seq(dt, score_total)),
|
|
| 140 |
- ("sample spread", lambda: greedy_min_seq(dt, score_spread)),
|
|
| 141 |
- ("furthest-nb", lambda: furthest_nb(dt)),
|
|
| 168 |
+ ("maximin", lambda: greedy_maximin(dt)),
|
|
| 142 | 169 |
] |
| 143 | 170 |
input("ready?")
|
| 144 | 171 |
for (name, method) in METHODS: |
| 145 | 172 |