test_lukes.py 3.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152
  1. from itertools import product
  2. import pytest
  3. import networkx as nx
  4. EWL = "e_weight"
  5. NWL = "n_weight"
  6. # first test from the Lukes original paper
  7. def paper_1_case(float_edge_wt=False, explicit_node_wt=True, directed=False):
  8. # problem-specific constants
  9. limit = 3
  10. # configuration
  11. if float_edge_wt:
  12. shift = 0.001
  13. else:
  14. shift = 0
  15. if directed:
  16. example_1 = nx.DiGraph()
  17. else:
  18. example_1 = nx.Graph()
  19. # graph creation
  20. example_1.add_edge(1, 2, **{EWL: 3 + shift})
  21. example_1.add_edge(1, 4, **{EWL: 2 + shift})
  22. example_1.add_edge(2, 3, **{EWL: 4 + shift})
  23. example_1.add_edge(2, 5, **{EWL: 6 + shift})
  24. # node weights
  25. if explicit_node_wt:
  26. nx.set_node_attributes(example_1, 1, NWL)
  27. wtu = NWL
  28. else:
  29. wtu = None
  30. # partitioning
  31. clusters_1 = {
  32. frozenset(x)
  33. for x in nx.community.lukes_partitioning(
  34. example_1, limit, node_weight=wtu, edge_weight=EWL
  35. )
  36. }
  37. return clusters_1
  38. # second test from the Lukes original paper
  39. def paper_2_case(explicit_edge_wt=True, directed=False):
  40. # problem specific constants
  41. byte_block_size = 32
  42. # configuration
  43. if directed:
  44. example_2 = nx.DiGraph()
  45. else:
  46. example_2 = nx.Graph()
  47. if explicit_edge_wt:
  48. edic = {EWL: 1}
  49. wtu = EWL
  50. else:
  51. edic = {}
  52. wtu = None
  53. # graph creation
  54. example_2.add_edge("name", "home_address", **edic)
  55. example_2.add_edge("name", "education", **edic)
  56. example_2.add_edge("education", "bs", **edic)
  57. example_2.add_edge("education", "ms", **edic)
  58. example_2.add_edge("education", "phd", **edic)
  59. example_2.add_edge("name", "telephone", **edic)
  60. example_2.add_edge("telephone", "home", **edic)
  61. example_2.add_edge("telephone", "office", **edic)
  62. example_2.add_edge("office", "no1", **edic)
  63. example_2.add_edge("office", "no2", **edic)
  64. example_2.nodes["name"][NWL] = 20
  65. example_2.nodes["education"][NWL] = 10
  66. example_2.nodes["bs"][NWL] = 1
  67. example_2.nodes["ms"][NWL] = 1
  68. example_2.nodes["phd"][NWL] = 1
  69. example_2.nodes["home_address"][NWL] = 8
  70. example_2.nodes["telephone"][NWL] = 8
  71. example_2.nodes["home"][NWL] = 8
  72. example_2.nodes["office"][NWL] = 4
  73. example_2.nodes["no1"][NWL] = 1
  74. example_2.nodes["no2"][NWL] = 1
  75. # partitioning
  76. clusters_2 = {
  77. frozenset(x)
  78. for x in nx.community.lukes_partitioning(
  79. example_2, byte_block_size, node_weight=NWL, edge_weight=wtu
  80. )
  81. }
  82. return clusters_2
  83. def test_paper_1_case():
  84. ground_truth = {frozenset([1, 4]), frozenset([2, 3, 5])}
  85. tf = (True, False)
  86. for flt, nwt, drc in product(tf, tf, tf):
  87. part = paper_1_case(flt, nwt, drc)
  88. assert part == ground_truth
  89. def test_paper_2_case():
  90. ground_truth = {
  91. frozenset(["education", "bs", "ms", "phd"]),
  92. frozenset(["name", "home_address"]),
  93. frozenset(["telephone", "home", "office", "no1", "no2"]),
  94. }
  95. tf = (True, False)
  96. for ewt, drc in product(tf, tf):
  97. part = paper_2_case(ewt, drc)
  98. assert part == ground_truth
  99. def test_mandatory_tree():
  100. not_a_tree = nx.complete_graph(4)
  101. with pytest.raises(nx.NotATree):
  102. nx.community.lukes_partitioning(not_a_tree, 5)
  103. def test_mandatory_integrality():
  104. byte_block_size = 32
  105. ex_1_broken = nx.DiGraph()
  106. ex_1_broken.add_edge(1, 2, **{EWL: 3.2})
  107. ex_1_broken.add_edge(1, 4, **{EWL: 2.4})
  108. ex_1_broken.add_edge(2, 3, **{EWL: 4.0})
  109. ex_1_broken.add_edge(2, 5, **{EWL: 6.3})
  110. ex_1_broken.nodes[1][NWL] = 1.2 # !
  111. ex_1_broken.nodes[2][NWL] = 1
  112. ex_1_broken.nodes[3][NWL] = 1
  113. ex_1_broken.nodes[4][NWL] = 1
  114. ex_1_broken.nodes[5][NWL] = 2
  115. with pytest.raises(TypeError):
  116. nx.community.lukes_partitioning(
  117. ex_1_broken, byte_block_size, node_weight=NWL, edge_weight=EWL
  118. )