Module 6 β€” Network disruption: who to remove first

Code
library(dplyr); library(ggplot2); library(readr); library(scales); library(leaflet); library(tidyr)
dismantle <- read_csv("../../outputs/dismantling.csv", show_col_types = FALSE)
auc <- read_csv("../../outputs/dismantling_auc.csv", show_col_types = FALSE)
wilcox <- read_csv("../../outputs/dismantling_wilcoxon.csv", show_col_types = FALSE)
blancos <- read_csv("../../outputs/blancos_disrupcion.csv", show_col_types = FALSE)
knitr::opts_chunk$set(message = FALSE, warning = FALSE)

In module 5 we identified the key actors. Now we answer the workshop’s question: who to remove first so the network stops working.

1. What is disruption and why is it the final goal?

  • Definition: intervention actions β€”judicial, financial or policeβ€” aimed at breaking the functional structure of the network so it can no longer operate as a system.
  • It does not seek to arrest every member (a rarely attainable goal), but to degrade the operational capacity by removing the key nodes.
  • The analogy: a criminal network is like a company β€” you do not need to fire every employee to break it; it is enough to remove those who sustain coordination and then those who lead each department.
  • In network terms: disruption = strategic vertex removal. The operational question is not β€œwho is most important?” but β€œwho to remove first so the network stops working with the least effort?”

2. Strategies: how we choose whom to remove

Five iterative removal strategies on the full chronnet, collapsed to undirected:

  • DEG (degree): removes the highest-degree vertex β€” decapitates hubs, those with the most connections.
  • BTW (betweenness): removes the highest-betweenness vertex β€” cuts bridges, those connecting circuits.
  • KB (Katz-Bonacich, \(\alpha = 0.1\), \(\beta = 1\)): weights contributions from the whole network attenuated by path length, \(c = \alpha A'c + \beta\) β€” rewards those well positioned and connected to other well-positioned nodes.
  • CI (collective influence, radius \(d = 3\)): removes the percolation-optimal vertex, \(CI_i = (k_i - 1)\sum_{j: d(i,j)=d}(k_j - 1)\) β€” counts not only its connections but those of its distance-3 neighborhood.
  • RND: random removal (baseline: what happens if we act with no network intelligence).

3. Protocols: how the removal is executed

Two protocols, mirroring how law enforcement acts in reality:

  • Sequential (\(b = 1\)) = individual arrests: one target is removed, the network is recomputed, the next is chosen. Slow but precise β€” every decision uses the current network.

  • Block (\(b = 5\)) = raid: the top 5 candidates are removed at once, as when there is no time to go one by one. Fast but coarse β€” the 5 were chosen on the network before the first one fell.

  • β€œbatch = 1” in the tables = individual protocol; β€œbatch = 5” = the raid.

  • After each removal, the graph is restricted to the largest connected piece: what matters is the piece that keeps operating, not the isolated remains.

4. How we measure the damage: three observables

At each simulation step \(i\):

\[p_i^{edges} = \frac{|E(g_i)|}{|E(g_0)|} \quad\text{(surviving edges)}\] \[p_i^{CC} = \mathrm{transitivity}(g_i) \quad\text{(residual clustering)}\] \[\frac{|\mathrm{LCC}(g_i)|}{N_0} \quad\text{(fraction of the network still connected)}\]

  • Effectiveness = area under the curve (AUC) of each trajectory: lower values = faster fragmentation.
  • Significance vs.Β chance = one-tailed paired Wilcoxon (strategy < RND) step by step, controlling for dependence between consecutive steps.

5. Results: AUC by strategy and protocol

Code
auc %>%
  mutate(across(starts_with("auc"), ~ round(.x, 3))) %>%
  arrange(batch, auc_edges) %>%
  knitr::kable(col.names = c("Strategy", "b", "Steps", "AUC edges", "AUC CC", "AUC LCC"))
Strategy b Steps AUC edges AUC CC AUC LCC
DEG 1 50 0.734 0.112 0.988
KB 1 50 0.735 0.110 0.988
BTW 1 50 0.739 0.118 0.988
CI 1 50 0.804 0.103 0.987
RND 1 50 0.980 0.118 0.989
DEG 5 10 0.719 0.111 0.987
KB 5 10 0.721 0.108 0.987
BTW 5 10 0.724 0.117 0.987
CI 5 10 0.791 0.102 0.986
RND 5 10 0.972 0.117 0.988

How to read the table:

  • Lower AUC = better attack (the curve fell faster).
  • Edges: DEG (0.734), KB (0.735) and BTW (0.739) lead; CI trails (0.804); RND last (0.980).
  • Clustering (CC): CI dominates (0.103, the lowest of all); chance stays at 0.118.
  • LCC: tie ~0.99 everywhere β€” nobody fragments the network at 2% removal.
Code
wilcox %>%
  mutate(p_wilcoxon = ifelse(p_wilcoxon < 0.001, "< 0.001", round(p_wilcoxon, 3))) %>%
  arrange(observable, batch, p_wilcoxon) %>%
  knitr::kable(col.names = c("Observable", "b", "Strategy", "p (Wilcoxon vs. RND)"))
Observable b Strategy p (Wilcoxon vs.Β RND)
cc 1 BTW 0.033
cc 1 DEG < 0.001
cc 1 KB < 0.001
cc 1 CI < 0.001
cc 5 KB 0.014
cc 5 DEG 0.019
cc 5 BTW 0.423
cc 5 CI < 0.001
edges 1 DEG < 0.001
edges 1 BTW < 0.001
edges 1 KB < 0.001
edges 1 CI < 0.001
edges 5 DEG < 0.001
edges 5 BTW < 0.001
edges 5 KB < 0.001
edges 5 CI < 0.001
lcc 1 DEG < 0.001
lcc 1 BTW < 0.001
lcc 1 KB < 0.001
lcc 1 CI < 0.001
lcc 5 DEG 0.002
lcc 5 BTW 0.002
lcc 5 KB 0.002
lcc 5 CI 0.004
  • The Wilcoxon \(p\) asks whether the advantage is consistent step by step or the product of a single lucky point.
  • Reading: every targeted strategy beats chance with p < 10⁻³ (batch 5) or p < 10⁻⁹ (batch 1) β€” the advantage is not noise.

6. Fragmentation trajectories

How to read the figure (rows = observable; columns = protocol):

  • X axis = fraction of nodes remaining: the attack advances right (intact network) β†’ left.
  • Y axis = surviving fraction of the observable; lower curve = better attack.
  • Edges row: targeted strategies separate early from chance; CI sits one step above (destroys edges slower than DEG/KB/BTW).
  • Clustering row: flat, close curves β€” cohesion is the most resistant; only CI drops clearly below chance.
  • LCC row: the 5 curves are stacked on top of each other (only the last one drawn, grey, is visible): no strategy fragments the network. The perfect overlap IS the result.
Code
d_long <- dismantle %>%
  pivot_longer(c(edges, cc, lcc), names_to = "observable", values_to = "valor") %>%
  mutate(observable = recode(observable,
                             edges = "Edge fraction", cc = "Transitivity",
                             lcc = "Normalized LCC size"),
         estrategia = factor(estrategia, levels = c("KB", "DEG", "BTW", "CI", "RND")))

ggplot(d_long, aes(fraccion, valor, color = estrategia)) +
  geom_line(linewidth = 1) +
  facet_grid(observable ~ factor(paste0("b = ", batch)), scales = "free_y") +
  scale_color_manual(values = c("KB" = "#B45309", "DEG" = "#0D9488", "BTW" = "#D4883A",
                                "CI" = "#64748B", "RND" = "#9CA3AF")) +
  labs(x = "Fraction of nodes remaining", y = "", color = "") +
  theme_minimal() + theme(legend.position = "bottom")

Criminal reading

  • Attacking with network intelligence erodes edges ~3Γ— faster than acting blind (AUC 0.72–0.74 targeted vs.Β 0.98 random; p < 10⁻⁹).
  • The damage concentrates on edges and cohesion: the giant component holds β€” even the targeted removal of 2% of the nodes fails to fragment it.
  • The robustness of a scale-free network admits no coup de grΓ’ce: it demands sustained operations.
  • The strategies do not tie: each destroys a different thing β€” that difference is the operational decision.

7. Top 15 priority targets

  • Method: combined ranking priority = rank(betweenness) + rank(strength) β€” lower = better target (topology + money).
  • Reading: #1 in betweenness and top-5 in money leads; moving volume without sitting on the path (Rosbank: strength #1, betweenness #14) falls behind.
  • The full JSON for the AI agent is in outputs/agente/blancos_disrupcion.json.
Code
blancos %>%
  slice_head(n = 15) %>%
  select(bank_name, country, intermediacion, fuerza, prioridad) %>%
  mutate(fuerza = dollar(fuerza)) %>%
  knitr::kable()
bank_name country intermediacion fuerza prioridad
Credit Suisse AG Switzerland 593752.55 $1,881,702,238 5
AS Expobank Latvia 334264.43 $2,666,430,134 5
Deutsche Bank AG Netherlands 318187.83 $1,664,219,281 8
Rosbank Russia 114564.01 $3,546,572,824 15
Credit Suisse Ag Switzerland 202362.34 $716,197,270 30
DBS Bank Ltd Singapore 208931.36 $671,430,098 31
Norvik Banka JSC Latvia 139885.34 $762,138,351 31
JSC Norvik Banka Latvia 262141.36 $513,755,534 35
AS Expobank Latvia 221234.31 $493,949,576 38
Hong Kong And Shanghai Banking Corp Hong Kong 91443.21 $875,138,633 38
Rosbank Russia 74597.52 $1,207,455,548 38
LTB Bank Latvia 108671.09 $574,837,983 42
Citibank N.A. United States 96260.65 $532,061,571 50
HSBC Hong Kong Hong Kong 219075.93 $315,367,995 51
Bank Soyuz Russia 55906.18 $805,642,191 51

8. Targets map

  • OpenStreetMap background; radius ∝ priority (lower priority = larger radius).
  • Layer switch to toggle the flows between targets (only pairs with documented money).
  • Tooltip: bank, country, priority, money and coordinates.
Code
readRDS("../../outputs/widgets/mapa_blancos.rds")

9. World flows map (full context)

  • The 500 largest flows; every bank at its headquarters with a full spatio-temporal tooltip.
  • OpenStreetMap background; layer control to toggle the edges.
Code
readRDS("../../outputs/widgets/mapa_flujos.rds")

10. Two-phase sequence: the operational decision

The results show a division of labor between the strategies:

  • Edges: DEG, KB and BTW lead tied (AUC 0.72–0.74) β€” and all far below chance (0.98): targeted attack removes edges ~3 times faster than acting blind.
  • Cohesion: CI dominates (CC AUC 0.103, the lowest of all): its distance-3 neighborhood disarms the triangles; it is the only strategy that erodes clustering faster than chance.
  • Global connectivity: tie (LCC AUC β‰ˆ 0.99): no strategy fragments the giant component at 2% β€” the network’s robustness is not beaten in the short term.

Practical recommendation, in two phases:

  1. Phase 1 β€” Isolate: BTW-type interventions on the bridges between communities. It is not the one that removes the most edges, but it leaves the circuits unable to communicate, and its effect accumulates: a cut bridge is not replaced.
  2. Phase 2 β€” Erode the cohesion: sustained CI-type operations on the surviving cores. It degrades clustering fastest β€” it disorganizes the local cell β€” and it is the only one compatible with a campaign of months, not a single day.

Criminal reading

  • Separating the objectives β€” isolate vs.Β disorganize β€” is the module’s central lesson.
  • A prosecutor who only chases β€œthose with the most money” (strength) leaves intact the bridges that rebuild the network.
  • One who only cuts bridges leaves whole communities operating locally.
  • The right sequence turns two mediocre operations into one effective strategy.