snappy 3.3__cp310-cp310-manylinux_2_24_aarch64.manylinux_2_28_aarch64.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (541) hide show
  1. snappy/CyOpenGL.cpython-310-aarch64-linux-gnu.so +0 -0
  2. snappy/SnapPy.cpython-310-aarch64-linux-gnu.so +0 -0
  3. snappy/SnapPy.ico +0 -0
  4. snappy/SnapPy.png +0 -0
  5. snappy/SnapPyHP.cpython-310-aarch64-linux-gnu.so +0 -0
  6. snappy/__init__.py +534 -0
  7. snappy/app.py +604 -0
  8. snappy/app_menus.py +372 -0
  9. snappy/browser.py +998 -0
  10. snappy/cache.py +25 -0
  11. snappy/canonical.py +249 -0
  12. snappy/cusps/__init__.py +280 -0
  13. snappy/cusps/cusp_area_matrix.py +98 -0
  14. snappy/cusps/cusp_areas_from_matrix.py +96 -0
  15. snappy/cusps/maximal_cusp_area_matrix.py +136 -0
  16. snappy/cusps/short_slopes_for_cusp.py +217 -0
  17. snappy/cusps/test.py +22 -0
  18. snappy/cusps/trig_cusp_area_matrix.py +63 -0
  19. snappy/database.py +454 -0
  20. snappy/db_utilities.py +79 -0
  21. snappy/decorated_isosig.py +717 -0
  22. snappy/dev/__init__.py +0 -0
  23. snappy/dev/extended_ptolemy/__init__.py +8 -0
  24. snappy/dev/extended_ptolemy/closed.py +106 -0
  25. snappy/dev/extended_ptolemy/complexVolumesClosed.py +149 -0
  26. snappy/dev/extended_ptolemy/direct.py +42 -0
  27. snappy/dev/extended_ptolemy/extended.py +406 -0
  28. snappy/dev/extended_ptolemy/giac_helper.py +43 -0
  29. snappy/dev/extended_ptolemy/giac_rur.py +129 -0
  30. snappy/dev/extended_ptolemy/gluing.py +46 -0
  31. snappy/dev/extended_ptolemy/phc_wrapper.py +220 -0
  32. snappy/dev/extended_ptolemy/printMatrices.py +70 -0
  33. snappy/dev/vericlosed/__init__.py +1 -0
  34. snappy/dev/vericlosed/computeApproxHyperbolicStructureNew.py +159 -0
  35. snappy/dev/vericlosed/computeApproxHyperbolicStructureOrb.py +90 -0
  36. snappy/dev/vericlosed/computeVerifiedHyperbolicStructure.py +111 -0
  37. snappy/dev/vericlosed/gimbalLoopFinder.py +130 -0
  38. snappy/dev/vericlosed/hyperbolicStructure.py +313 -0
  39. snappy/dev/vericlosed/krawczykCertifiedEdgeLengthsEngine.py +165 -0
  40. snappy/dev/vericlosed/oneVertexTruncatedComplex.py +122 -0
  41. snappy/dev/vericlosed/orb/__init__.py +1 -0
  42. snappy/dev/vericlosed/orb/orb_solution_for_snappea_finite_triangulation_mac +0 -0
  43. snappy/dev/vericlosed/parseVertexGramMatrixFile.py +47 -0
  44. snappy/dev/vericlosed/polishApproxHyperbolicStructure.py +61 -0
  45. snappy/dev/vericlosed/test.py +54 -0
  46. snappy/dev/vericlosed/truncatedComplex.py +176 -0
  47. snappy/dev/vericlosed/verificationError.py +58 -0
  48. snappy/dev/vericlosed/verifyHyperbolicStructureEngine.py +177 -0
  49. snappy/doc/_images/SnapPy-196.png +0 -0
  50. snappy/doc/_images/m004_paper_plane_on_systole.jpg +0 -0
  51. snappy/doc/_images/m125_paper_plane.jpg +0 -0
  52. snappy/doc/_images/mac.png +0 -0
  53. snappy/doc/_images/o9_00000_systole_paper_plane.jpg +0 -0
  54. snappy/doc/_images/o9_00000_systole_paper_plane_closer.jpg +0 -0
  55. snappy/doc/_images/plink-action.png +0 -0
  56. snappy/doc/_images/ubuntu.png +0 -0
  57. snappy/doc/_images/win7.png +0 -0
  58. snappy/doc/_sources/additional_classes.rst.txt +40 -0
  59. snappy/doc/_sources/bugs.rst.txt +14 -0
  60. snappy/doc/_sources/censuses.rst.txt +52 -0
  61. snappy/doc/_sources/credits.rst.txt +81 -0
  62. snappy/doc/_sources/development.rst.txt +261 -0
  63. snappy/doc/_sources/index.rst.txt +215 -0
  64. snappy/doc/_sources/installing.rst.txt +249 -0
  65. snappy/doc/_sources/manifold.rst.txt +6 -0
  66. snappy/doc/_sources/manifoldhp.rst.txt +46 -0
  67. snappy/doc/_sources/news.rst.txt +425 -0
  68. snappy/doc/_sources/other.rst.txt +25 -0
  69. snappy/doc/_sources/platonic_census.rst.txt +20 -0
  70. snappy/doc/_sources/plink.rst.txt +102 -0
  71. snappy/doc/_sources/ptolemy.rst.txt +66 -0
  72. snappy/doc/_sources/ptolemy_classes.rst.txt +42 -0
  73. snappy/doc/_sources/ptolemy_examples1.rst.txt +298 -0
  74. snappy/doc/_sources/ptolemy_examples2.rst.txt +363 -0
  75. snappy/doc/_sources/ptolemy_examples3.rst.txt +301 -0
  76. snappy/doc/_sources/ptolemy_examples4.rst.txt +61 -0
  77. snappy/doc/_sources/ptolemy_prelim.rst.txt +105 -0
  78. snappy/doc/_sources/screenshots.rst.txt +21 -0
  79. snappy/doc/_sources/snap.rst.txt +87 -0
  80. snappy/doc/_sources/snappy.rst.txt +28 -0
  81. snappy/doc/_sources/spherogram.rst.txt +103 -0
  82. snappy/doc/_sources/todo.rst.txt +47 -0
  83. snappy/doc/_sources/triangulation.rst.txt +11 -0
  84. snappy/doc/_sources/tutorial.rst.txt +49 -0
  85. snappy/doc/_sources/verify.rst.txt +210 -0
  86. snappy/doc/_sources/verify_internals.rst.txt +79 -0
  87. snappy/doc/_static/SnapPy-horizontal-128.png +0 -0
  88. snappy/doc/_static/SnapPy.ico +0 -0
  89. snappy/doc/_static/_sphinx_javascript_frameworks_compat.js +123 -0
  90. snappy/doc/_static/basic.css +906 -0
  91. snappy/doc/_static/css/badge_only.css +1 -0
  92. snappy/doc/_static/css/fonts/Roboto-Slab-Bold.woff +0 -0
  93. snappy/doc/_static/css/fonts/Roboto-Slab-Bold.woff2 +0 -0
  94. snappy/doc/_static/css/fonts/Roboto-Slab-Regular.woff +0 -0
  95. snappy/doc/_static/css/fonts/Roboto-Slab-Regular.woff2 +0 -0
  96. snappy/doc/_static/css/fonts/fontawesome-webfont.eot +0 -0
  97. snappy/doc/_static/css/fonts/fontawesome-webfont.svg +2671 -0
  98. snappy/doc/_static/css/fonts/fontawesome-webfont.ttf +0 -0
  99. snappy/doc/_static/css/fonts/fontawesome-webfont.woff +0 -0
  100. snappy/doc/_static/css/fonts/fontawesome-webfont.woff2 +0 -0
  101. snappy/doc/_static/css/fonts/lato-bold-italic.woff +0 -0
  102. snappy/doc/_static/css/fonts/lato-bold-italic.woff2 +0 -0
  103. snappy/doc/_static/css/fonts/lato-bold.woff +0 -0
  104. snappy/doc/_static/css/fonts/lato-bold.woff2 +0 -0
  105. snappy/doc/_static/css/fonts/lato-normal-italic.woff +0 -0
  106. snappy/doc/_static/css/fonts/lato-normal-italic.woff2 +0 -0
  107. snappy/doc/_static/css/fonts/lato-normal.woff +0 -0
  108. snappy/doc/_static/css/fonts/lato-normal.woff2 +0 -0
  109. snappy/doc/_static/css/theme.css +4 -0
  110. snappy/doc/_static/doctools.js +149 -0
  111. snappy/doc/_static/documentation_options.js +13 -0
  112. snappy/doc/_static/file.png +0 -0
  113. snappy/doc/_static/fonts/Lato/lato-bold.eot +0 -0
  114. snappy/doc/_static/fonts/Lato/lato-bold.ttf +0 -0
  115. snappy/doc/_static/fonts/Lato/lato-bold.woff +0 -0
  116. snappy/doc/_static/fonts/Lato/lato-bold.woff2 +0 -0
  117. snappy/doc/_static/fonts/Lato/lato-bolditalic.eot +0 -0
  118. snappy/doc/_static/fonts/Lato/lato-bolditalic.ttf +0 -0
  119. snappy/doc/_static/fonts/Lato/lato-bolditalic.woff +0 -0
  120. snappy/doc/_static/fonts/Lato/lato-bolditalic.woff2 +0 -0
  121. snappy/doc/_static/fonts/Lato/lato-italic.eot +0 -0
  122. snappy/doc/_static/fonts/Lato/lato-italic.ttf +0 -0
  123. snappy/doc/_static/fonts/Lato/lato-italic.woff +0 -0
  124. snappy/doc/_static/fonts/Lato/lato-italic.woff2 +0 -0
  125. snappy/doc/_static/fonts/Lato/lato-regular.eot +0 -0
  126. snappy/doc/_static/fonts/Lato/lato-regular.ttf +0 -0
  127. snappy/doc/_static/fonts/Lato/lato-regular.woff +0 -0
  128. snappy/doc/_static/fonts/Lato/lato-regular.woff2 +0 -0
  129. snappy/doc/_static/fonts/RobotoSlab/roboto-slab-v7-bold.eot +0 -0
  130. snappy/doc/_static/fonts/RobotoSlab/roboto-slab-v7-bold.ttf +0 -0
  131. snappy/doc/_static/fonts/RobotoSlab/roboto-slab-v7-bold.woff +0 -0
  132. snappy/doc/_static/fonts/RobotoSlab/roboto-slab-v7-bold.woff2 +0 -0
  133. snappy/doc/_static/fonts/RobotoSlab/roboto-slab-v7-regular.eot +0 -0
  134. snappy/doc/_static/fonts/RobotoSlab/roboto-slab-v7-regular.ttf +0 -0
  135. snappy/doc/_static/fonts/RobotoSlab/roboto-slab-v7-regular.woff +0 -0
  136. snappy/doc/_static/fonts/RobotoSlab/roboto-slab-v7-regular.woff2 +0 -0
  137. snappy/doc/_static/jquery.js +2 -0
  138. snappy/doc/_static/js/badge_only.js +1 -0
  139. snappy/doc/_static/js/theme.js +1 -0
  140. snappy/doc/_static/js/versions.js +228 -0
  141. snappy/doc/_static/language_data.js +192 -0
  142. snappy/doc/_static/minus.png +0 -0
  143. snappy/doc/_static/plus.png +0 -0
  144. snappy/doc/_static/pygments.css +75 -0
  145. snappy/doc/_static/searchtools.js +635 -0
  146. snappy/doc/_static/snappy_furo.css +33 -0
  147. snappy/doc/_static/snappy_sphinx_rtd_theme.css +42 -0
  148. snappy/doc/_static/sphinx_highlight.js +154 -0
  149. snappy/doc/additional_classes.html +1500 -0
  150. snappy/doc/bugs.html +132 -0
  151. snappy/doc/censuses.html +453 -0
  152. snappy/doc/credits.html +184 -0
  153. snappy/doc/development.html +385 -0
  154. snappy/doc/doc-latest/additional_classes.html +1500 -0
  155. snappy/doc/doc-latest/bugs.html +132 -0
  156. snappy/doc/doc-latest/censuses.html +453 -0
  157. snappy/doc/doc-latest/credits.html +184 -0
  158. snappy/doc/doc-latest/development.html +385 -0
  159. snappy/doc/doc-latest/genindex.html +1349 -0
  160. snappy/doc/doc-latest/index.html +287 -0
  161. snappy/doc/doc-latest/installing.html +346 -0
  162. snappy/doc/doc-latest/manifold.html +3632 -0
  163. snappy/doc/doc-latest/manifoldhp.html +180 -0
  164. snappy/doc/doc-latest/news.html +438 -0
  165. snappy/doc/doc-latest/objects.inv +0 -0
  166. snappy/doc/doc-latest/other.html +160 -0
  167. snappy/doc/doc-latest/platonic_census.html +376 -0
  168. snappy/doc/doc-latest/plink.html +210 -0
  169. snappy/doc/doc-latest/ptolemy.html +253 -0
  170. snappy/doc/doc-latest/ptolemy_classes.html +1144 -0
  171. snappy/doc/doc-latest/ptolemy_examples1.html +409 -0
  172. snappy/doc/doc-latest/ptolemy_examples2.html +471 -0
  173. snappy/doc/doc-latest/ptolemy_examples3.html +414 -0
  174. snappy/doc/doc-latest/ptolemy_examples4.html +195 -0
  175. snappy/doc/doc-latest/ptolemy_prelim.html +248 -0
  176. snappy/doc/doc-latest/py-modindex.html +165 -0
  177. snappy/doc/doc-latest/screenshots.html +141 -0
  178. snappy/doc/doc-latest/search.html +135 -0
  179. snappy/doc/doc-latest/searchindex.js +1 -0
  180. snappy/doc/doc-latest/snap.html +202 -0
  181. snappy/doc/doc-latest/snappy.html +181 -0
  182. snappy/doc/doc-latest/spherogram.html +1346 -0
  183. snappy/doc/doc-latest/todo.html +166 -0
  184. snappy/doc/doc-latest/triangulation.html +1676 -0
  185. snappy/doc/doc-latest/tutorial.html +159 -0
  186. snappy/doc/doc-latest/verify.html +330 -0
  187. snappy/doc/doc-latest/verify_internals.html +1235 -0
  188. snappy/doc/genindex.html +1349 -0
  189. snappy/doc/index.html +287 -0
  190. snappy/doc/installing.html +346 -0
  191. snappy/doc/manifold.html +3632 -0
  192. snappy/doc/manifoldhp.html +180 -0
  193. snappy/doc/news.html +438 -0
  194. snappy/doc/objects.inv +0 -0
  195. snappy/doc/other.html +160 -0
  196. snappy/doc/platonic_census.html +376 -0
  197. snappy/doc/plink.html +210 -0
  198. snappy/doc/ptolemy.html +253 -0
  199. snappy/doc/ptolemy_classes.html +1144 -0
  200. snappy/doc/ptolemy_examples1.html +409 -0
  201. snappy/doc/ptolemy_examples2.html +471 -0
  202. snappy/doc/ptolemy_examples3.html +414 -0
  203. snappy/doc/ptolemy_examples4.html +195 -0
  204. snappy/doc/ptolemy_prelim.html +248 -0
  205. snappy/doc/py-modindex.html +165 -0
  206. snappy/doc/screenshots.html +141 -0
  207. snappy/doc/search.html +135 -0
  208. snappy/doc/searchindex.js +1 -0
  209. snappy/doc/snap.html +202 -0
  210. snappy/doc/snappy.html +181 -0
  211. snappy/doc/spherogram.html +1346 -0
  212. snappy/doc/todo.html +166 -0
  213. snappy/doc/triangulation.html +1676 -0
  214. snappy/doc/tutorial.html +159 -0
  215. snappy/doc/verify.html +330 -0
  216. snappy/doc/verify_internals.html +1235 -0
  217. snappy/drilling/__init__.py +456 -0
  218. snappy/drilling/barycentric.py +103 -0
  219. snappy/drilling/constants.py +5 -0
  220. snappy/drilling/crush.py +270 -0
  221. snappy/drilling/cusps.py +125 -0
  222. snappy/drilling/debug.py +242 -0
  223. snappy/drilling/epsilons.py +6 -0
  224. snappy/drilling/exceptions.py +55 -0
  225. snappy/drilling/moves.py +620 -0
  226. snappy/drilling/peripheral_curves.py +210 -0
  227. snappy/drilling/perturb.py +188 -0
  228. snappy/drilling/shorten.py +36 -0
  229. snappy/drilling/subdivide.py +274 -0
  230. snappy/drilling/test.py +23 -0
  231. snappy/drilling/test_cases.py +132 -0
  232. snappy/drilling/tracing.py +351 -0
  233. snappy/exceptions.py +26 -0
  234. snappy/export_stl.py +120 -0
  235. snappy/exterior_to_link/__init__.py +2 -0
  236. snappy/exterior_to_link/barycentric_geometry.py +463 -0
  237. snappy/exterior_to_link/exceptions.py +6 -0
  238. snappy/exterior_to_link/geodesic_map.json +14408 -0
  239. snappy/exterior_to_link/hyp_utils.py +112 -0
  240. snappy/exterior_to_link/link_projection.py +323 -0
  241. snappy/exterior_to_link/main.py +198 -0
  242. snappy/exterior_to_link/mcomplex_with_expansion.py +261 -0
  243. snappy/exterior_to_link/mcomplex_with_link.py +687 -0
  244. snappy/exterior_to_link/mcomplex_with_memory.py +162 -0
  245. snappy/exterior_to_link/pl_utils.py +491 -0
  246. snappy/exterior_to_link/put_in_S3.py +156 -0
  247. snappy/exterior_to_link/rational_linear_algebra.py +130 -0
  248. snappy/exterior_to_link/rational_linear_algebra_wrapped.py +135 -0
  249. snappy/exterior_to_link/simplify_to_base_tri.py +114 -0
  250. snappy/exterior_to_link/stored_moves.py +475 -0
  251. snappy/exterior_to_link/test.py +31 -0
  252. snappy/filedialog.py +28 -0
  253. snappy/geometric_structure/__init__.py +212 -0
  254. snappy/geometric_structure/cusp_neighborhood/__init__.py +3 -0
  255. snappy/geometric_structure/cusp_neighborhood/complex_cusp_cross_section.py +691 -0
  256. snappy/geometric_structure/cusp_neighborhood/cusp_cross_section_base.py +480 -0
  257. snappy/geometric_structure/cusp_neighborhood/exceptions.py +41 -0
  258. snappy/geometric_structure/cusp_neighborhood/real_cusp_cross_section.py +294 -0
  259. snappy/geometric_structure/cusp_neighborhood/tiles_for_cusp_neighborhood.py +156 -0
  260. snappy/geometric_structure/cusp_neighborhood/vertices.py +35 -0
  261. snappy/geometric_structure/geodesic/__init__.py +0 -0
  262. snappy/geometric_structure/geodesic/add_core_curves.py +152 -0
  263. snappy/geometric_structure/geodesic/avoid_core_curves.py +369 -0
  264. snappy/geometric_structure/geodesic/canonical_representatives.py +52 -0
  265. snappy/geometric_structure/geodesic/check_away_from_core_curve.py +60 -0
  266. snappy/geometric_structure/geodesic/constants.py +6 -0
  267. snappy/geometric_structure/geodesic/exceptions.py +22 -0
  268. snappy/geometric_structure/geodesic/fixed_points.py +106 -0
  269. snappy/geometric_structure/geodesic/geodesic_start_point_info.py +435 -0
  270. snappy/geometric_structure/geodesic/graph_trace_helper.py +67 -0
  271. snappy/geometric_structure/geodesic/line.py +30 -0
  272. snappy/geometric_structure/geodesic/multiplicity.py +127 -0
  273. snappy/geometric_structure/geodesic/tiles_for_geodesic.py +128 -0
  274. snappy/geometric_structure/test.py +22 -0
  275. snappy/gui.py +121 -0
  276. snappy/horoviewer.py +443 -0
  277. snappy/hyperboloid/__init__.py +212 -0
  278. snappy/hyperboloid/distances.py +259 -0
  279. snappy/hyperboloid/horoball.py +19 -0
  280. snappy/hyperboloid/line.py +35 -0
  281. snappy/hyperboloid/point.py +9 -0
  282. snappy/hyperboloid/triangle.py +29 -0
  283. snappy/info_icon.gif +0 -0
  284. snappy/infowindow.py +65 -0
  285. snappy/isometry_signature.py +389 -0
  286. snappy/len_spec/__init__.py +609 -0
  287. snappy/len_spec/geodesic_info.py +129 -0
  288. snappy/len_spec/geodesic_key_info_dict.py +116 -0
  289. snappy/len_spec/geodesic_piece.py +146 -0
  290. snappy/len_spec/geometric_structure.py +182 -0
  291. snappy/len_spec/geometry.py +136 -0
  292. snappy/len_spec/length_spectrum_geodesic_info.py +185 -0
  293. snappy/len_spec/spine.py +128 -0
  294. snappy/len_spec/test.py +24 -0
  295. snappy/len_spec/test_cases.py +69 -0
  296. snappy/len_spec/tile.py +276 -0
  297. snappy/len_spec/word.py +86 -0
  298. snappy/manifolds/HTWKnots/alternating.gz +0 -0
  299. snappy/manifolds/HTWKnots/nonalternating.gz +0 -0
  300. snappy/manifolds/__init__.py +3 -0
  301. snappy/margulis/__init__.py +332 -0
  302. snappy/margulis/cusp_neighborhood_neighborhood.py +66 -0
  303. snappy/margulis/geodesic_neighborhood.py +152 -0
  304. snappy/margulis/margulis_info.py +21 -0
  305. snappy/margulis/mu_from_neighborhood_pair.py +175 -0
  306. snappy/margulis/neighborhood.py +29 -0
  307. snappy/margulis/test.py +22 -0
  308. snappy/math_basics.py +187 -0
  309. snappy/matrix.py +525 -0
  310. snappy/number.py +657 -0
  311. snappy/numeric_output_checker.py +345 -0
  312. snappy/pari.py +41 -0
  313. snappy/phone_home.py +57 -0
  314. snappy/polyviewer.py +259 -0
  315. snappy/ptolemy/__init__.py +17 -0
  316. snappy/ptolemy/component.py +103 -0
  317. snappy/ptolemy/coordinates.py +2290 -0
  318. snappy/ptolemy/fieldExtensions.py +153 -0
  319. snappy/ptolemy/findLoops.py +473 -0
  320. snappy/ptolemy/geometricRep.py +59 -0
  321. snappy/ptolemy/homology.py +165 -0
  322. snappy/ptolemy/magma/default.magma_template +229 -0
  323. snappy/ptolemy/magma/radicalsOfPrimaryDecomposition.magma_template +79 -0
  324. snappy/ptolemy/manifoldMethods.py +395 -0
  325. snappy/ptolemy/matrix.py +350 -0
  326. snappy/ptolemy/numericalSolutionsToGroebnerBasis.py +113 -0
  327. snappy/ptolemy/polynomial.py +856 -0
  328. snappy/ptolemy/processComponents.py +173 -0
  329. snappy/ptolemy/processFileBase.py +247 -0
  330. snappy/ptolemy/processFileDispatch.py +46 -0
  331. snappy/ptolemy/processMagmaFile.py +392 -0
  332. snappy/ptolemy/processRurFile.py +150 -0
  333. snappy/ptolemy/ptolemyGeneralizedObstructionClass.py +102 -0
  334. snappy/ptolemy/ptolemyObstructionClass.py +64 -0
  335. snappy/ptolemy/ptolemyVariety.py +995 -0
  336. snappy/ptolemy/ptolemyVarietyPrimeIdealGroebnerBasis.py +140 -0
  337. snappy/ptolemy/reginaWrapper.py +698 -0
  338. snappy/ptolemy/regina_testing_files/DT_mcbbiceaibjklmdfgh__sl2_c0.magma_out.bz2 +0 -0
  339. snappy/ptolemy/regina_testing_files/DT_mcbbiceaibjklmdfgh__sl2_c1.magma_out.bz2 +0 -0
  340. snappy/ptolemy/regina_testing_files/DT_mcbbiceaibjklmdfgh__sl2_c2.magma_out.bz2 +0 -0
  341. snappy/ptolemy/regina_testing_files/DT_mcbbiceaibjklmdfgh__sl2_c3.magma_out.bz2 +0 -0
  342. snappy/ptolemy/regina_testing_files/DT_mcbbiceaibjklmdfgh__sl2_c4.magma_out.bz2 +0 -0
  343. snappy/ptolemy/regina_testing_files/DT_mcbbiceaibjklmdfgh__sl2_c5.magma_out.bz2 +0 -0
  344. snappy/ptolemy/regina_testing_files/DT_mcbbiceaibjklmdfgh__sl2_c6.magma_out.bz2 +0 -0
  345. snappy/ptolemy/regina_testing_files/DT_mcbbiceaibjklmdfgh__sl2_c7.magma_out.bz2 +0 -0
  346. snappy/ptolemy/regina_testing_files_generalized/m003__sl3_c0.magma_out.bz2 +0 -0
  347. snappy/ptolemy/regina_testing_files_generalized/m003__sl3_c1.magma_out.bz2 +0 -0
  348. snappy/ptolemy/regina_testing_files_generalized/m015__sl2_c0.magma_out.bz2 +0 -0
  349. snappy/ptolemy/regina_testing_files_generalized/m015__sl2_c1.magma_out.bz2 +0 -0
  350. snappy/ptolemy/regina_testing_files_generalized/m015__sl3_c0.magma_out.bz2 +0 -0
  351. snappy/ptolemy/regina_testing_files_generalized/m015__sl3_c1.magma_out.bz2 +0 -0
  352. snappy/ptolemy/rur.py +545 -0
  353. snappy/ptolemy/solutionsToPrimeIdealGroebnerBasis.py +277 -0
  354. snappy/ptolemy/test.py +1126 -0
  355. snappy/ptolemy/testing_files/3_1__sl2_c0.magma_out.bz2 +0 -0
  356. snappy/ptolemy/testing_files/3_1__sl2_c1.magma_out.bz2 +0 -0
  357. snappy/ptolemy/testing_files/4_1__sl2_c0.magma_out.bz2 +0 -0
  358. snappy/ptolemy/testing_files/4_1__sl2_c1.magma_out.bz2 +0 -0
  359. snappy/ptolemy/testing_files/4_1__sl3_c0.magma_out.bz2 +0 -0
  360. snappy/ptolemy/testing_files/4_1__sl4_c0.magma_out.bz2 +0 -0
  361. snappy/ptolemy/testing_files/4_1__sl4_c1.magma_out.bz2 +0 -0
  362. snappy/ptolemy/testing_files/5_2__sl2_c0.magma_out.bz2 +0 -0
  363. snappy/ptolemy/testing_files/5_2__sl2_c1.magma_out.bz2 +0 -0
  364. snappy/ptolemy/testing_files/DT_mcbbiceaibjklmdfgh__sl2_c0.magma_out.bz2 +0 -0
  365. snappy/ptolemy/testing_files/DT_mcbbiceaibjklmdfgh__sl2_c1.magma_out.bz2 +0 -0
  366. snappy/ptolemy/testing_files/DT_mcbbiceaibjklmdfgh__sl2_c2.magma_out.bz2 +0 -0
  367. snappy/ptolemy/testing_files/DT_mcbbiceaibjklmdfgh__sl2_c3.magma_out.bz2 +0 -0
  368. snappy/ptolemy/testing_files/DT_mcbbiceaibjklmdfgh__sl2_c4.magma_out.bz2 +0 -0
  369. snappy/ptolemy/testing_files/DT_mcbbiceaibjklmdfgh__sl2_c5.magma_out.bz2 +0 -0
  370. snappy/ptolemy/testing_files/DT_mcbbiceaibjklmdfgh__sl2_c6.magma_out.bz2 +0 -0
  371. snappy/ptolemy/testing_files/DT_mcbbiceaibjklmdfgh__sl2_c7.magma_out.bz2 +0 -0
  372. snappy/ptolemy/testing_files/data/pgl2/OrientableCuspedCensus/03_tetrahedra/m019__sl2_c0.magma_out +95 -0
  373. snappy/ptolemy/testing_files/data/pgl2/OrientableCuspedCensus/03_tetrahedra/m019__sl2_c1.magma_out +95 -0
  374. snappy/ptolemy/testing_files/m015__sl3_c0.magma_out.bz2 +0 -0
  375. snappy/ptolemy/testing_files/m135__sl2_c0.magma_out.bz2 +0 -0
  376. snappy/ptolemy/testing_files/m135__sl2_c1.magma_out.bz2 +0 -0
  377. snappy/ptolemy/testing_files/m135__sl2_c2.magma_out.bz2 +0 -0
  378. snappy/ptolemy/testing_files/m135__sl2_c3.magma_out.bz2 +0 -0
  379. snappy/ptolemy/testing_files/m135__sl2_c4.magma_out.bz2 +0 -0
  380. snappy/ptolemy/testing_files/m135__sl2_c5.magma_out.bz2 +0 -0
  381. snappy/ptolemy/testing_files/m135__sl2_c6.magma_out.bz2 +0 -0
  382. snappy/ptolemy/testing_files/m135__sl2_c7.magma_out.bz2 +0 -0
  383. snappy/ptolemy/testing_files/s000__sl2_c0.magma_out.bz2 +0 -0
  384. snappy/ptolemy/testing_files/s000__sl2_c1.magma_out.bz2 +0 -0
  385. snappy/ptolemy/testing_files/t00000__sl2_c0.magma_out.bz2 +0 -0
  386. snappy/ptolemy/testing_files/t00000__sl2_c1.magma_out.bz2 +0 -0
  387. snappy/ptolemy/testing_files/v0000__sl2_c0.magma_out.bz2 +0 -0
  388. snappy/ptolemy/testing_files/v0000__sl2_c1.magma_out.bz2 +0 -0
  389. snappy/ptolemy/testing_files/v0000__sl2_c2.magma_out.bz2 +0 -0
  390. snappy/ptolemy/testing_files/v0000__sl2_c3.magma_out.bz2 +0 -0
  391. snappy/ptolemy/testing_files_generalized/m003__sl2_c0.magma_out.bz2 +0 -0
  392. snappy/ptolemy/testing_files_generalized/m003__sl2_c1.magma_out.bz2 +0 -0
  393. snappy/ptolemy/testing_files_generalized/m003__sl3_c0.magma_out.bz2 +0 -0
  394. snappy/ptolemy/testing_files_generalized/m003__sl3_c1.magma_out.bz2 +0 -0
  395. snappy/ptolemy/testing_files_generalized/m004__sl2_c0.magma_out.bz2 +0 -0
  396. snappy/ptolemy/testing_files_generalized/m004__sl2_c1.magma_out.bz2 +0 -0
  397. snappy/ptolemy/testing_files_generalized/m015__sl2_c1.magma_out.bz2 +0 -0
  398. snappy/ptolemy/testing_files_generalized/m015__sl3_c0.magma_out.bz2 +0 -0
  399. snappy/ptolemy/testing_files_rur/m052__sl3_c0.rur.bz2 +0 -0
  400. snappy/ptolemy/utilities.py +236 -0
  401. snappy/raytracing/__init__.py +64 -0
  402. snappy/raytracing/additional_horospheres.py +64 -0
  403. snappy/raytracing/additional_len_spec_choices.py +63 -0
  404. snappy/raytracing/cohomology_fractal.py +197 -0
  405. snappy/raytracing/eyeball.py +124 -0
  406. snappy/raytracing/finite_raytracing_data.py +237 -0
  407. snappy/raytracing/finite_viewer.py +590 -0
  408. snappy/raytracing/geodesic_tube_info.py +174 -0
  409. snappy/raytracing/geodesics.py +246 -0
  410. snappy/raytracing/geodesics_window.py +258 -0
  411. snappy/raytracing/gui_utilities.py +293 -0
  412. snappy/raytracing/hyperboloid_navigation.py +556 -0
  413. snappy/raytracing/hyperboloid_utilities.py +234 -0
  414. snappy/raytracing/ideal_raytracing_data.py +592 -0
  415. snappy/raytracing/inside_viewer.py +974 -0
  416. snappy/raytracing/pack.py +22 -0
  417. snappy/raytracing/raytracing_data.py +126 -0
  418. snappy/raytracing/raytracing_view.py +454 -0
  419. snappy/raytracing/shaders/Eye.png +0 -0
  420. snappy/raytracing/shaders/NonGeometric.png +0 -0
  421. snappy/raytracing/shaders/__init__.py +101 -0
  422. snappy/raytracing/shaders/fragment.glsl +1744 -0
  423. snappy/raytracing/test.py +29 -0
  424. snappy/raytracing/tooltip.py +146 -0
  425. snappy/raytracing/upper_halfspace_utilities.py +98 -0
  426. snappy/raytracing/view_scale_controller.py +98 -0
  427. snappy/raytracing/zoom_slider/__init__.py +263 -0
  428. snappy/raytracing/zoom_slider/inward.png +0 -0
  429. snappy/raytracing/zoom_slider/inward18.png +0 -0
  430. snappy/raytracing/zoom_slider/outward.png +0 -0
  431. snappy/raytracing/zoom_slider/outward18.png +0 -0
  432. snappy/raytracing/zoom_slider/test.py +20 -0
  433. snappy/sage_helper.py +119 -0
  434. snappy/settings.py +407 -0
  435. snappy/shell.py +53 -0
  436. snappy/snap/__init__.py +117 -0
  437. snappy/snap/character_varieties.py +375 -0
  438. snappy/snap/find_field.py +372 -0
  439. snappy/snap/fox_milnor.py +271 -0
  440. snappy/snap/fundamental_polyhedron.py +569 -0
  441. snappy/snap/generators.py +39 -0
  442. snappy/snap/interval_reps.py +81 -0
  443. snappy/snap/kernel_structures.py +128 -0
  444. snappy/snap/mcomplex_base.py +18 -0
  445. snappy/snap/nsagetools.py +716 -0
  446. snappy/snap/peripheral/__init__.py +1 -0
  447. snappy/snap/peripheral/dual_cellulation.py +219 -0
  448. snappy/snap/peripheral/link.py +127 -0
  449. snappy/snap/peripheral/peripheral.py +159 -0
  450. snappy/snap/peripheral/surface.py +522 -0
  451. snappy/snap/peripheral/test.py +35 -0
  452. snappy/snap/polished_reps.py +335 -0
  453. snappy/snap/shapes.py +152 -0
  454. snappy/snap/slice_obs_HKL/__init__.py +194 -0
  455. snappy/snap/slice_obs_HKL/basics.py +236 -0
  456. snappy/snap/slice_obs_HKL/direct.py +217 -0
  457. snappy/snap/slice_obs_HKL/poly_norm.py +212 -0
  458. snappy/snap/slice_obs_HKL/rep_theory.py +424 -0
  459. snappy/snap/t3mlite/__init__.py +2 -0
  460. snappy/snap/t3mlite/arrow.py +243 -0
  461. snappy/snap/t3mlite/corner.py +22 -0
  462. snappy/snap/t3mlite/edge.py +172 -0
  463. snappy/snap/t3mlite/face.py +37 -0
  464. snappy/snap/t3mlite/files.py +211 -0
  465. snappy/snap/t3mlite/homology.py +53 -0
  466. snappy/snap/t3mlite/linalg.py +419 -0
  467. snappy/snap/t3mlite/mcomplex.py +1499 -0
  468. snappy/snap/t3mlite/perm4.py +320 -0
  469. snappy/snap/t3mlite/setup.py +12 -0
  470. snappy/snap/t3mlite/simplex.py +199 -0
  471. snappy/snap/t3mlite/spun.py +297 -0
  472. snappy/snap/t3mlite/surface.py +519 -0
  473. snappy/snap/t3mlite/test.py +20 -0
  474. snappy/snap/t3mlite/test_vs_regina.py +86 -0
  475. snappy/snap/t3mlite/tetrahedron.py +109 -0
  476. snappy/snap/t3mlite/vertex.py +42 -0
  477. snappy/snap/test.py +139 -0
  478. snappy/snap/utilities.py +288 -0
  479. snappy/test.py +213 -0
  480. snappy/test_cases.py +263 -0
  481. snappy/testing.py +131 -0
  482. snappy/tiling/__init__.py +2 -0
  483. snappy/tiling/dict_based_set.py +79 -0
  484. snappy/tiling/floor.py +49 -0
  485. snappy/tiling/hyperboloid_dict.py +54 -0
  486. snappy/tiling/iter_utils.py +78 -0
  487. snappy/tiling/lifted_tetrahedron.py +22 -0
  488. snappy/tiling/lifted_tetrahedron_set.py +54 -0
  489. snappy/tiling/quotient_dict.py +70 -0
  490. snappy/tiling/real_hash_dict.py +164 -0
  491. snappy/tiling/test.py +23 -0
  492. snappy/tiling/tile.py +224 -0
  493. snappy/tiling/triangle.py +33 -0
  494. snappy/tkterminal.py +920 -0
  495. snappy/twister/__init__.py +20 -0
  496. snappy/twister/main.py +646 -0
  497. snappy/twister/surfaces/S_0_1 +3 -0
  498. snappy/twister/surfaces/S_0_2 +3 -0
  499. snappy/twister/surfaces/S_0_4 +7 -0
  500. snappy/twister/surfaces/S_0_4_Lantern +8 -0
  501. snappy/twister/surfaces/S_1 +3 -0
  502. snappy/twister/surfaces/S_1_1 +4 -0
  503. snappy/twister/surfaces/S_1_2 +5 -0
  504. snappy/twister/surfaces/S_1_2_5 +6 -0
  505. snappy/twister/surfaces/S_2 +6 -0
  506. snappy/twister/surfaces/S_2_1 +8 -0
  507. snappy/twister/surfaces/S_2_heeg +10 -0
  508. snappy/twister/surfaces/S_3 +8 -0
  509. snappy/twister/surfaces/S_3_1 +10 -0
  510. snappy/twister/surfaces/S_4_1 +12 -0
  511. snappy/twister/surfaces/S_5_1 +14 -0
  512. snappy/twister/surfaces/heeg_fig8 +9 -0
  513. snappy/twister/twister_core.cpython-310-aarch64-linux-gnu.so +0 -0
  514. snappy/upper_halfspace/__init__.py +146 -0
  515. snappy/upper_halfspace/ideal_point.py +29 -0
  516. snappy/verify/__init__.py +13 -0
  517. snappy/verify/canonical.py +542 -0
  518. snappy/verify/complex_volume/__init__.py +18 -0
  519. snappy/verify/complex_volume/adjust_torsion.py +86 -0
  520. snappy/verify/complex_volume/closed.py +168 -0
  521. snappy/verify/complex_volume/compute_ptolemys.py +90 -0
  522. snappy/verify/complex_volume/cusped.py +56 -0
  523. snappy/verify/complex_volume/extended_bloch.py +201 -0
  524. snappy/verify/cusp_translations.py +85 -0
  525. snappy/verify/edge_equations.py +80 -0
  526. snappy/verify/exceptions.py +254 -0
  527. snappy/verify/hyperbolicity.py +224 -0
  528. snappy/verify/interval_newton_shapes_engine.py +523 -0
  529. snappy/verify/interval_tree.py +400 -0
  530. snappy/verify/krawczyk_shapes_engine.py +518 -0
  531. snappy/verify/real_algebra.py +286 -0
  532. snappy/verify/shapes.py +25 -0
  533. snappy/verify/square_extensions.py +1005 -0
  534. snappy/verify/test.py +72 -0
  535. snappy/verify/volume.py +128 -0
  536. snappy/version.py +2 -0
  537. snappy-3.3.dist-info/METADATA +58 -0
  538. snappy-3.3.dist-info/RECORD +541 -0
  539. snappy-3.3.dist-info/WHEEL +6 -0
  540. snappy-3.3.dist-info/entry_points.txt +2 -0
  541. snappy-3.3.dist-info/top_level.txt +28 -0
snappy/test.py ADDED
@@ -0,0 +1,213 @@
1
+ import os
2
+ import sys
3
+ import glob
4
+ import argparse
5
+ import snappy
6
+ import snappy.snap.test
7
+ import spherogram.test
8
+ import snappy.matrix
9
+ import snappy.verify.test
10
+ import snappy.geometric_structure.test
11
+ import snappy.ptolemy.test
12
+ import snappy.tiling.test
13
+ import snappy.cusps.test
14
+ import snappy.raytracing.test
15
+ import snappy.len_spec.test
16
+ import snappy.margulis.test
17
+ import snappy.drilling.test
18
+ import snappy.canonical
19
+ import snappy.cusps.cusp_area_matrix
20
+ import snappy.cusps.cusp_areas_from_matrix
21
+ import snappy.isometry_signature
22
+ import snappy.exterior_to_link.test
23
+ import snappy.pari
24
+ import snappy.test_cases
25
+ import snappy.numeric_output_checker
26
+ import snappy.cusps
27
+
28
+ from snappy.sage_helper import _within_sage
29
+ from snappy.testing import (doctest_modules, cyopengl_works,
30
+ tk_root, root_is_fake, DocTestParser)
31
+
32
+ # Augment tests for SnapPy with those that Cython missed
33
+
34
+ missed_classes = ['Triangulation', 'Manifold',
35
+ 'AbelianGroup', 'FundamentalGroup', 'HolonomyGroup',
36
+ 'DirichletDomain', 'CuspNeighborhood', 'SymmetryGroup',
37
+ 'AlternatingKnotExteriors', 'NonalternatingKnotExteriors']
38
+
39
+ for A in missed_classes:
40
+ snappy.SnapPy.__test__[A + '_extra'] = getattr(snappy, A).__doc__
41
+ snappy.SnapPyHP.__test__[A + '_extra'] = getattr(snappy, A).__doc__
42
+
43
+ # some things we don't want to test at the extension module level
44
+ identify_tests = [x for x in snappy.SnapPyHP.__test__
45
+ if x.startswith('Manifold.identify')]
46
+ triangulation_tests = [x for x in snappy.SnapPyHP.__test__
47
+ if x.startswith('get_triangulation_tester')]
48
+ browser_tests = [x for x in snappy.SnapPyHP.__test__
49
+ if x.startswith('Manifold.browse')]
50
+ for key in identify_tests + triangulation_tests + browser_tests:
51
+ snappy.SnapPyHP.__test__.pop(key)
52
+
53
+ def additional_doctests(verbose=False, print_info=True):
54
+ """
55
+ I noticed that some of my changes to move code from here into
56
+ its own files caused some loss of test coverage.
57
+
58
+ In a panic, adding them explicitly here.
59
+
60
+ There ought to be a better way to do this...
61
+ """
62
+
63
+ globs = {'Manifold' : snappy.Manifold,
64
+ 'ManifoldHP' : snappy.ManifoldHP}
65
+ return doctest_modules(
66
+ [ snappy.isometry_signature,
67
+ snappy.canonical,
68
+ snappy.cusps.cusp_area_matrix,
69
+ snappy.cusps.cusp_areas_from_matrix
70
+ ],
71
+ verbose=verbose,
72
+ print_info=print_info,
73
+ extraglobs = globs)
74
+ additional_doctests.__name__ = 'snappy.<HARD TO REACH>'
75
+
76
+ modules = [
77
+ snappy.exterior_to_link.test.run_doctests,
78
+ snappy.numeric_output_checker.run_doctests,
79
+ snappy.number,
80
+ snappy.SnapPy,
81
+ snappy.SnapPyHP,
82
+ snappy.database,
83
+ additional_doctests,
84
+ snappy,
85
+ snappy.cusps.test.run_doctests,
86
+ snappy.snap.test.run_doctests,
87
+ snappy.matrix,
88
+ snappy.geometric_structure.test.run_doctests,
89
+ snappy.tiling.test.run_doctests,
90
+ snappy.cusps.test.run_doctests,
91
+ snappy.raytracing.test.run_doctests,
92
+ snappy.len_spec.test.run_doctests,
93
+ snappy.margulis.test.run_doctests,
94
+ snappy.drilling.test.run_doctests,
95
+ snappy.ptolemy.test.run_doctests,
96
+ spherogram.test.run_doctests,
97
+ snappy.verify.test.run_doctests,
98
+ snappy.test_cases
99
+ ]
100
+
101
+ slow_modules = [
102
+ snappy.ptolemy.test.run_ptolemy_tests
103
+ ]
104
+
105
+ def graphics_failures(verbose, windows, use_modernopengl):
106
+ if cyopengl_works():
107
+ print("Testing graphics ...")
108
+ import snappy.CyOpenGL
109
+ result = doctest_modules([snappy.CyOpenGL], verbose=verbose).failed
110
+ snappy.Manifold('m004').dirichlet_domain().view().test()
111
+ snappy.Manifold('m125').cusp_neighborhood().view().test()
112
+ if use_modernopengl:
113
+ snappy.Manifold('m004').inside_view().test()
114
+ snappy.Manifold('4_1').browse().test(use_modernopengl=use_modernopengl)
115
+ snappy.ManifoldHP('m004').dirichlet_domain().view().test()
116
+ snappy.ManifoldHP('m125').cusp_neighborhood().view().test()
117
+ if use_modernopengl:
118
+ snappy.ManifoldHP('m004').inside_view().test()
119
+ if root_is_fake():
120
+ root = tk_root()
121
+ if root:
122
+ if windows:
123
+ print('Close the root window to finish.')
124
+ else:
125
+ print('The windows will close in a few seconds.\n'
126
+ 'Specify -w or --windows to avoid this.')
127
+ root.after(7000, root.destroy)
128
+ root.mainloop()
129
+ else:
130
+ print("***Warning***: Could not test CyOpenGL.")
131
+ try:
132
+ import snappy.CyOpenGL
133
+ print("Reason: Unsuitable Tk configuration for CyOpenGL")
134
+ except ImportError as e:
135
+ print("Reason: CyOpenGL could not be imported, %r" % e)
136
+ result = 0
137
+ return result
138
+
139
+
140
+ def check_for_docs():
141
+ path = os.path.dirname(snappy.__file__)
142
+ match = os.path.join(path, 'doc', '*.html')
143
+ html_files = [os.path.basename(file) for file in glob.glob(match)]
144
+ if len(html_files) > 20 and 'index.html' in html_files:
145
+ print('HTML docs are included.')
146
+ else:
147
+ print('WARNING: HTML docs are missing!')
148
+
149
+
150
+ def runtests(verbose=False,
151
+ quick=False,
152
+ windows=False,
153
+ use_modernopengl=True,
154
+ graphics=True):
155
+
156
+ # The default PARI stacksize can (slightly) overflow, causing
157
+ # doctests to fail.
158
+ snappy.pari.allocatemem(2**24, 2**25, silent=True)
159
+
160
+ DocTestParser.use_cymodernopengl = use_modernopengl
161
+
162
+ all_modules = modules
163
+ if not quick:
164
+ all_modules += slow_modules
165
+
166
+ result = doctest_modules(
167
+ all_modules, verbose=verbose, print_info=True)
168
+
169
+ if not quick:
170
+ print()
171
+ spherogram.links.test.run()
172
+ print('\nAll doctests:\n %s failures out of %s tests.' % result)
173
+
174
+ if graphics:
175
+ num_graphics_failures = graphics_failures(
176
+ verbose=verbose,
177
+ windows=windows,
178
+ use_modernopengl=use_modernopengl)
179
+ else:
180
+ num_graphics_failures = 0
181
+
182
+ print('Pari stacksize', snappy.pari.stacksize(),
183
+ 'max stack size', snappy.pari.stacksizemax())
184
+
185
+ check_for_docs()
186
+ return result.failed + num_graphics_failures
187
+
188
+
189
+ if __name__ == '__main__':
190
+ verbose = False
191
+ quick = False
192
+ windows = False
193
+ use_modernopengl = True
194
+ graphics = True
195
+
196
+ useful_args = [arg for arg in sys.argv[1:] if not arg.startswith('-psn_')]
197
+
198
+ parser = argparse.ArgumentParser()
199
+ parser.add_argument('-v', '--verbose', action='store_true',
200
+ help='show additional information')
201
+ parser.add_argument('-q', '--quick', action='store_true',
202
+ help='skip ptolemy and spherogram.links tests.')
203
+ parser.add_argument('-w', '--windows', action='store_true',
204
+ help='keep windows open until user closes root window.')
205
+ parser.add_argument('-s', '--skip-modern-opengl', action='store_false',
206
+ dest='use_modernopengl',
207
+ help='skip tests requiring OpenGL 3.2 or later.')
208
+ parser.add_argument('-g', '--skip-gui', action='store_false',
209
+ dest='graphics',
210
+ help='skip tests bringing up GUI windows.')
211
+ args = parser.parse_args(useful_args)
212
+
213
+ sys.exit(runtests(**vars(args)))
snappy/test_cases.py ADDED
@@ -0,0 +1,263 @@
1
+ """
2
+ IMPORTANT: Python only recognises this as a doc string if there is
3
+ nothing before it. In particular, add any includes after the doc string.
4
+
5
+ Doc tests that we do not want to show up in the documentation.
6
+
7
+ Decorated isomorphism signature
8
+ -------------------------------
9
+
10
+ An example where the isosig doesn't pick up the identity perm
11
+ because the lexicographic order of the perm interacts with the
12
+ matrices.
13
+
14
+ >>> T = Triangulation("L6n1(0,0)(0,0)(0,0)")
15
+ >>> T.triangulation_isosig()
16
+ 'gLMzQbcdefffaelaaai_acbBaabCbbabbBC'
17
+
18
+ Test that slopes are computed correctly.
19
+
20
+ >>> M=Manifold("L14n63023(-5,1)(5,1)(10,1)")
21
+ >>> M.triangulation_isosig(decorated=False, ignore_orientation=False)
22
+ 'vLLvvLLMALQQzQQceillmnppqrlmrqtruututiivimllaelaqxrvdoxqltt'
23
+
24
+ The canonical orientation (used to compute the unoriented isosig)
25
+ is the reverse of the actual orientation:
26
+
27
+ >>> M.triangulation_isosig(decorated=False)
28
+ 'vLLvLLPwPQLAMPQcefikkmnplkopqrsttutuuiixvimqlippawidlabavth'
29
+ >>> Mop = M.copy()
30
+ >>> Mop.reverse_orientation()
31
+ >>> Mop.triangulation_isosig(decorated=False, ignore_orientation=False)
32
+ 'vLLvLLPwPQLAMPQcefikkmnplkopqrsttutuuiixvimqlippawidlabavth'
33
+
34
+ So we expect the oriented isometry signature to flip when neither the isomorphism
35
+ signature nor its decoration capture the orientation.
36
+
37
+ The following is a baked version of snappy.decorated_isosig.test_slope_transformations().
38
+ The 32 calls to ManifoldHP.isometry_signature are just too expensive for the test suite.
39
+
40
+ >>> for ignore_cusp_ordering in [False, True]:
41
+ ... for ignore_curves in [False, True]:
42
+ ... for ignore_curve_orientations in [False, True]:
43
+ ... for ignore_filling_orientations in [False, True]:
44
+ ... for ignore_orientation in [False, True]:
45
+ ... isosig = M.triangulation_isosig(
46
+ ... ignore_cusp_ordering = ignore_cusp_ordering,
47
+ ... ignore_curves = ignore_curves,
48
+ ... ignore_curve_orientations = ignore_curve_orientations,
49
+ ... ignore_filling_orientations = ignore_filling_orientations,
50
+ ... ignore_orientation = ignore_orientation)
51
+ ... print(isosig)
52
+ vLLvvLLMALQQzQQceillmnppqrlmrqtruututiivimllaelaqxrvdoxqltt_dcbaabBBBbBaBbCbBbCb(-5,1)(5,1)(10,1)(0,0)
53
+ vLLvLLPwPQLAMPQcefikkmnplkopqrsttutuuiixvimqlippawidlabavth_cabdBacbbBCbaBBBbabB(-5,1)(5,1)(10,1)(0,0)
54
+ vLLvvLLMALQQzQQceillmnppqrlmrqtruututiivimllaelaqxrvdoxqltt_dcbaabBBBbBaBbCbBbCb(-5,1)(5,1)(10,1)(0,0)
55
+ vLLvLLPwPQLAMPQcefikkmnplkopqrsttutuuiixvimqlippawidlabavth_cabdBacbbBCbaBBBbabB(-5,1)(5,1)(10,1)(0,0)
56
+ vLLvvLLMALQQzQQceillmnppqrlmrqtruututiivimllaelaqxrvdoxqltt_dcbaabBBbBbabBcBbBcB(-5,1)(-5,-1)(-10,-1)(0,0)
57
+ vLLvLLPwPQLAMPQcefikkmnplkopqrsttutuuiixvimqlippawidlabavth_cabdbacbbBcBabBBbaBb(5,1)(5,-1)(-10,1)(0,0)
58
+ vLLvvLLMALQQzQQceillmnppqrlmrqtruututiivimllaelaqxrvdoxqltt_dcbaabBBbBbabBcBbBcB(-5,1)(5,1)(10,1)(0,0)
59
+ vLLvLLPwPQLAMPQcefikkmnplkopqrsttutuuiixvimqlippawidlabavth_cabdbacbbBcBabBBbaBb(5,1)(-5,1)(-10,1)(0,0)
60
+ vLLvvLLMALQQzQQceillmnppqrlmrqtruututiivimllaelaqxrvdoxqltt_dcba(-1,-6)(-6,5)(-12,11)(0,0)
61
+ vLLvLLPwPQLAMPQcefikkmnplkopqrsttutuuiixvimqlippawidlabavth_cabd(-7,-1)(-3,4)(1,11)(0,0)
62
+ vLLvvLLMALQQzQQceillmnppqrlmrqtruututiivimllaelaqxrvdoxqltt_dcba(1,6)(-6,5)(-12,11)(0,0)
63
+ vLLvLLPwPQLAMPQcefikkmnplkopqrsttutuuiixvimqlippawidlabavth_cabd(7,1)(-3,4)(1,11)(0,0)
64
+ vLLvvLLMALQQzQQceillmnppqrlmrqtruututiivimllaelaqxrvdoxqltt_dcba(-1,-6)(-6,5)(-12,11)(0,0)
65
+ vLLvLLPwPQLAMPQcefikkmnplkopqrsttutuuiixvimqlippawidlabavth_cabd(-7,-1)(-3,4)(1,11)(0,0)
66
+ vLLvvLLMALQQzQQceillmnppqrlmrqtruututiivimllaelaqxrvdoxqltt_dcba(1,6)(-6,5)(-12,11)(0,0)
67
+ vLLvLLPwPQLAMPQcefikkmnplkopqrsttutuuiixvimqlippawidlabavth_cabd(7,1)(-3,4)(1,11)(0,0)
68
+ vLLvvLLMALQQzQQceillmnppqrlmrqtruututiivimllaelaqxrvdoxqltt_BbCbBbCbBbBaabBB(0,0)(10,1)(5,1)(-5,1)
69
+ vLLvLLPwPQLAMPQcefikkmnplkopqrsttutuuiixvimqlippawidlabavth_aBBBBacbbBCbbabB(10,1)(-5,1)(5,1)(0,0)
70
+ vLLvvLLMALQQzQQceillmnppqrlmrqtruututiivimllaelaqxrvdoxqltt_BbCbBbCbBbBaabBB(0,0)(10,1)(5,1)(-5,1)
71
+ vLLvLLPwPQLAMPQcefikkmnplkopqrsttutuuiixvimqlippawidlabavth_aBBBBacbbBCbbabB(10,1)(-5,1)(5,1)(0,0)
72
+ vLLvvLLMALQQzQQceillmnppqrlmrqtruututiivimllaelaqxrvdoxqltt_bBcBbBcBbBbaabBB(0,0)(-10,-1)(-5,-1)(-5,1)
73
+ vLLvLLPwPQLAMPQcefikkmnplkopqrsttutuuiixvimqlippawidlabavth_abBBbacbbBcBbaBb(-10,1)(5,1)(5,-1)(0,0)
74
+ vLLvvLLMALQQzQQceillmnppqrlmrqtruututiivimllaelaqxrvdoxqltt_bBcBbBcBbBbaabBB(0,0)(10,1)(5,1)(-5,1)
75
+ vLLvLLPwPQLAMPQcefikkmnplkopqrsttutuuiixvimqlippawidlabavth_abBBbacbbBcBbaBb(-10,1)(5,1)(-5,1)(0,0)
76
+ vLLvvLLMALQQzQQceillmnppqrlmrqtruututiivimllaelaqxrvdoxqltt(0,0)(-12,11)(-6,5)(6,-1)
77
+ vLLvLLPwPQLAMPQcefikkmnplkopqrsttutuuiixvimqlippawidlabavth(1,11)(-7,-1)(-3,4)(0,0)
78
+ vLLvvLLMALQQzQQceillmnppqrlmrqtruututiivimllaelaqxrvdoxqltt(0,0)(-12,11)(-6,5)(-6,1)
79
+ vLLvLLPwPQLAMPQcefikkmnplkopqrsttutuuiixvimqlippawidlabavth(1,11)(7,1)(-3,4)(0,0)
80
+ vLLvvLLMALQQzQQceillmnppqrlmrqtruututiivimllaelaqxrvdoxqltt(0,0)(-12,11)(-6,5)(6,-1)
81
+ vLLvLLPwPQLAMPQcefikkmnplkopqrsttutuuiixvimqlippawidlabavth(1,11)(-7,-1)(-3,4)(0,0)
82
+ vLLvvLLMALQQzQQceillmnppqrlmrqtruututiivimllaelaqxrvdoxqltt(0,0)(-12,11)(-6,5)(-6,1)
83
+ vLLvLLPwPQLAMPQcefikkmnplkopqrsttutuuiixvimqlippawidlabavth(1,11)(7,1)(-3,4)(0,0)
84
+
85
+ The special case where we do not encode the matrices and have the identity perm
86
+ and need it:
87
+
88
+ >>> T = Triangulation('ovLMvvPQQQccddlmnijklmnmnlgvfamtvfblhaumx_BBbacBbacBbaBCaB(312,241)(332,441)(3322,1441)(726,541)')
89
+ >>> T.homology()
90
+ Z/4684873938228
91
+ >>> isosig = T.triangulation_isosig(ignore_curves=True, ignore_cusp_ordering=False)
92
+ >>> isosig
93
+ 'ovLMvvPQQQccddlmnijklmnmnlgvfamtvfblhaumx_abcd(71,312)(-1105,332)(-8085,3322)(726,1993)'
94
+ >>> Triangulation(isosig).homology()
95
+ Z/4684873938228
96
+
97
+
98
+ isometry_signature
99
+ ------------------
100
+
101
+ >>> M = Manifold('m004(1,2)')
102
+ >>> M.isometry_signature()
103
+ 'cPcbbbiht(3,2)'
104
+
105
+ sage: M.isometry_signature(verified=True)
106
+ 'cPcbbbiht(3,2)'
107
+
108
+ >>> M = ManifoldHP('m004(1,2)')
109
+ >>> M.isometry_signature()
110
+ 'cPcbbbiht(3,2)'
111
+
112
+ sage: M.isometry_signature(verified=True) # Test bug reported by Nathan
113
+ 'cPcbbbiht(3,2)'
114
+
115
+ # Cases where the drilled manifold had a canonical cell decomposition
116
+ # with non-tetrahedral cells.
117
+
118
+ >>> M = Manifold('m137(3,2)')
119
+ >>> M.isometry_signature()
120
+ 'sLLvwzvQPAQPQccghmiljkpmqnoorqrrqfafaoaqoofaoooqqaf(3,2)'
121
+
122
+ sage: M.isometry_signature(verified=True)
123
+ 'sLLvwzvQPAQPQccghmiljkpmqnoorqrrqfafaoaqoofaoooqqaf(3,2)'
124
+
125
+ >>> M = ManifoldHP('m137(3,2)')
126
+ >>> M.isometry_signature()
127
+ 'sLLvwzvQPAQPQccghmiljkpmqnoorqrrqfafaoaqoofaoooqqaf(3,2)'
128
+
129
+ sage: M.isometry_signature(verified=True)
130
+ 'sLLvwzvQPAQPQccghmiljkpmqnoorqrrqfafaoaqoofaoooqqaf(3,2)'
131
+
132
+ sage: M.isometry_signature(verified=True, exact_bits_prec_and_degrees=[]) # doctest: +ELLIPSIS +IGNORE_EXCEPTION_DETAIL
133
+ Traceback (most recent call last):
134
+ ...
135
+ RuntimeError: Could not compute or verify canonical retriangulation of drilled manifold. Geodesic was: abCDaDAd.
136
+
137
+ Test isometry_signature's ignore_orientation
138
+
139
+ >>> M = Manifold("m006")
140
+ >>> M.isometry_signature(ignore_orientation=False)
141
+ 'eLMkaccddjgbaj'
142
+ >>> M.isometry_signature(ignore_orientation=True)
143
+ 'eLAkaccddngbak'
144
+ >>> M.isometry_signature() # default value
145
+ 'eLAkaccddngbak'
146
+ >>> M.dehn_fill((3,4))
147
+ >>> M.isometry_signature(ignore_orientation=False)
148
+ 'eLMkaccddjgbaj(-1,4)'
149
+ >>> M.isometry_signature(ignore_orientation=True)
150
+ 'eLAkaccddngbak(-3,4)'
151
+
152
+ Test isometry_signature's of_link and filling.
153
+
154
+ >>> Manifold("o9_44206(2,3)").isometry_signature(of_link=True)
155
+ 'jLLvMQQacggfiihhijkkjkehhtb_abBabBbabaab'
156
+
157
+ Class hierarchy
158
+ ---------------
159
+
160
+ >>> isinstance(Manifold("m004"), Triangulation)
161
+ True
162
+
163
+ >>> isinstance(ManifoldHP("m004"), TriangulationHP)
164
+ True
165
+
166
+ Low precision and high precision comparisons
167
+ --------------------------------------------
168
+ >>> M = Manifold("m004")
169
+ >>> Mhp = Manifold("m004")
170
+ >>> N = Manifold("m003")
171
+ >>> Nhp = Manifold("m003")
172
+ >>> M.is_isometric_to(M)
173
+ True
174
+ >>> M.is_isometric_to(Mhp)
175
+ True
176
+ >>> Mhp.is_isometric_to(M)
177
+ True
178
+ >>> Mhp.is_isometric_to(Mhp)
179
+ True
180
+ >>> M.is_isometric_to(N)
181
+ False
182
+ >>> M.is_isometric_to(Nhp)
183
+ False
184
+ >>> Mhp.is_isometric_to(N)
185
+ False
186
+ >>> Mhp.is_isometric_to(Nhp)
187
+ False
188
+
189
+ >>> O = Triangulation("mvvLALQQQhfghjjlilkjklaaaaaffffffff",
190
+ ... remove_finite_vertices = False)
191
+ >>> O.has_finite_vertices()
192
+ True
193
+ >>> Ohp = TriangulationHP("mvvLALQQQhfghjjlilkjklaaaaaffffffff",
194
+ ... remove_finite_vertices = False)
195
+ >>> Ohp.has_finite_vertices()
196
+ True
197
+
198
+ >>> len(O.isomorphisms_to(O))
199
+ 8
200
+ >>> len(O.isomorphisms_to(Ohp))
201
+ 8
202
+ >>> len(Ohp.isomorphisms_to(O))
203
+ 8
204
+ >>> len(Ohp.isomorphisms_to(Ohp))
205
+ 8
206
+ >>> len(M.isomorphisms_to(O))
207
+ 0
208
+ >>> len(M.isomorphisms_to(Ohp))
209
+ 0
210
+ >>> len(Mhp.isomorphisms_to(O))
211
+ 0
212
+ >>> len(Mhp.isomorphisms_to(Ohp))
213
+ 0
214
+
215
+ Canonical retriangulation
216
+ -------------------------
217
+
218
+ Some cases that should be rejected
219
+
220
+ >>> M = Manifold("m004(3,4)")
221
+ >>> M.canonical_retriangulation() # doctest: +ELLIPSIS
222
+ Traceback (most recent call last):
223
+ ...
224
+ ValueError: Canonical retriangulation needs all cusps to be complete.
225
+
226
+ sage: M.canonical_retriangulation(verified=True) # doctest: +ELLIPSIS
227
+ Traceback (most recent call last):
228
+ ...
229
+ ValueError: Canonical retriangulation needs all cusps to be complete.
230
+
231
+ Cusp areas
232
+ ----------
233
+
234
+ >>> M = Manifold('o9_44210')
235
+ >>> M.cusp_areas(policy='greedy') # doctest: +NUMERIC9
236
+ [7.053940530873898, 3.2712450270, 2.7091590087]
237
+ >>> M.cusp_areas(policy='greedy', first_cusps=[]) # doctest: +NUMERIC9
238
+ [7.053940530873898, 3.2712450270, 2.7091590087]
239
+ >>> M.cusp_areas(policy='greedy', first_cusps=[0,]) # doctest: +NUMERIC9
240
+ [7.053940530873898, 3.2712450270, 2.7091590087]
241
+ >>> M.cusp_areas(policy='greedy', first_cusps=[0,1]) # doctest: +NUMERIC9
242
+ [7.053940530873898, 3.2712450270, 2.7091590087]
243
+ >>> M.cusp_areas(policy='greedy', first_cusps=[0,1,2]) # doctest: +NUMERIC9
244
+ [7.053940530873898, 3.2712450270, 2.7091590087]
245
+ >>> M.cusp_areas(policy='greedy', first_cusps=[0,2,1]) # doctest: +NUMERIC9
246
+ [7.053940530873898, 2.3513135103, 3.7690945490]
247
+ >>> M.cusp_areas(policy='greedy', first_cusps=[1,]) # doctest: +NUMERIC9
248
+ [2.30025338030798, 10.0315765558665, 0.883442685721903]
249
+
250
+ Cusp translations
251
+ -----------------
252
+
253
+ >>> M = Manifold("s776")
254
+ >>> M.cusp_translations(policy = 'greedy', first_cusps = [], bits_prec = 100) # doctest: +NUMERIC21
255
+ [(0.70710678118654752440084436210 + 1.8708286933869706927918743662*I, 2.8284271247461900976033774484), (0.35355339059327376220042218105 + 0.93541434669348534639593718308*I, 1.4142135623730950488016887242), (0.35355339059327376220042218105 + 0.93541434669348534639593718308*I, 1.4142135623730950488016887242)]
256
+
257
+
258
+ """
259
+
260
+ if not __doc__:
261
+ raise Exception("doc string with tests was not recognized.")
262
+
263
+ from . import Manifold, ManifoldHP, Triangulation, TriangulationHP
snappy/testing.py ADDED
@@ -0,0 +1,131 @@
1
+ from .numeric_output_checker import NumericOutputChecker
2
+ from .sage_helper import _within_sage
3
+
4
+ import doctest
5
+ import getopt
6
+ import re
7
+ import sys
8
+ import types
9
+
10
+ # Used for doctesting
11
+ _gui_status = {}
12
+
13
+ try:
14
+ from snappy.gui import Tk_
15
+ _gui_status['tk'] = True
16
+ except ImportError:
17
+ _gui_status['tk'] = False
18
+ if _gui_status['tk']:
19
+ try:
20
+ import snappy.CyOpenGL
21
+ _gui_status['cyopengl'] = True
22
+ except:
23
+ _gui_status['cyopengl'] = False
24
+ else:
25
+ _gui_status['cyopengl'] = False
26
+ _gui_status['fake_root'] = False
27
+
28
+ def cyopengl_works():
29
+ if not _gui_status['cyopengl']:
30
+ return False
31
+ # if we are running the tests from the snappy app the default root will
32
+ # already exist -- it will be the tkterminal window. Otherwise, we open
33
+ # a root window here to serve as the master of all of the GUI windows
34
+ # which get created during testing.
35
+ if _gui_status['tk'] and not Tk_._default_root:
36
+ try:
37
+ root = Tk_.Tk()
38
+ if sys.platform not in ('linux', 'linux2'):
39
+ root.withdraw()
40
+ except:
41
+ # tkinter loads OK but is not able to get a display.
42
+ _gui_status['tk'] = _gui_status['cyopengl'] = False
43
+ return _gui_status['cyopengl']
44
+
45
+
46
+ def tk_root():
47
+ if _gui_status['tk']:
48
+ return Tk_._default_root
49
+ else:
50
+ return None
51
+
52
+ def root_is_fake():
53
+ return _gui_status['fake_root']
54
+
55
+ class DocTestParser(doctest.DocTestParser):
56
+ use_cyopengl = False
57
+ use_cymodernopengl = True
58
+ use_sage = _within_sage
59
+
60
+ def parse(self, string, name='<string>'):
61
+ string = re.subn(
62
+ r'#doctest: \+CYOPENGL',
63
+ '' if DocTestParser.use_cyopengl else '#doctest: +SKIP',
64
+ string)[0]
65
+
66
+ string = re.subn(
67
+ r'#doctest: \+CYMODERNOPENGL',
68
+ (''
69
+ if (DocTestParser.use_cyopengl and
70
+ DocTestParser.use_cymodernopengl)
71
+ else '#doctest: +SKIP'),
72
+ string)[0]
73
+
74
+ if DocTestParser.use_sage:
75
+ string = re.subn(r'(\n\s*)sage:|(\A\s*)sage:',
76
+ r'\g<1>>>>',
77
+ string)[0]
78
+ return doctest.DocTestParser.parse(self, string, name)
79
+
80
+ if _within_sage:
81
+ try:
82
+ from sage.all import PSL, BraidGroup
83
+ except ImportError:
84
+ import sage.groups.perm_gps.permgroup_element
85
+ from sage.groups.perm_gps.permgroup_named import PSL
86
+ from sage.groups.braid import BraidGroup
87
+ globs = {'PSL': PSL, 'BraidGroup': BraidGroup}
88
+ else:
89
+ globs = {}
90
+
91
+ def print_results(module, results):
92
+ root = tk_root()
93
+ # Platform specific hacks to make running the tests work.
94
+ if root and not root_is_fake():
95
+ if sys.platform in ('linux', 'linux2'):
96
+ root.deiconify()
97
+ root.update_idletasks()
98
+ else:
99
+ root.update()
100
+ print(module.__name__ + ':')
101
+ print(' %s failures out of %s tests.' % (results.failed,
102
+ results.attempted))
103
+
104
+ def doctest_modules(modules, verbose=False, print_info=False, extraglobs={}):
105
+ finder = doctest.DocTestFinder(parser=DocTestParser())
106
+ full_extraglobals = globs.copy()
107
+ full_extraglobals.update(extraglobs)
108
+ failed, attempted = 0, 0
109
+ for module in modules:
110
+ if isinstance(module, types.ModuleType):
111
+ runner = doctest.DocTestRunner(checker=NumericOutputChecker(), verbose=verbose)
112
+ for test in finder.find(module, extraglobs=full_extraglobals):
113
+ runner.run(test)
114
+ result = runner.summarize()
115
+ else:
116
+ result = module(verbose=verbose, print_info=False)
117
+ failed += result.failed
118
+ attempted += result.attempted
119
+ if print_info:
120
+ print_results(module, result)
121
+
122
+ if print_info:
123
+ print('\nAll doctests:\n %s failures out of %s tests.' % (failed, attempted))
124
+ return doctest.TestResults(failed, attempted)
125
+
126
+ def run_doctests_as_main(run_doctests):
127
+ optlist, args = getopt.getopt(sys.argv[1:], 'v', ['verbose'])
128
+ verbose = len(optlist) > 0
129
+ results = run_doctests(verbose=verbose, print_info=True)
130
+ sys.exit(results.failed)
131
+
@@ -0,0 +1,2 @@
1
+ # Tiling H^3 or quotients of H^3
2
+
@@ -0,0 +1,79 @@
1
+ class DictBasedSet:
2
+ """
3
+ This class can be constructed from a dictionary with keys in A.
4
+
5
+ The resulting object is a set of A.
6
+
7
+ >>> fruit_set = DictBasedSet(dict())
8
+ >>> fruit_set.add('Apple')
9
+ True
10
+ >>> fruit_set.add('Banana')
11
+ True
12
+ >>> fruit_set.add('Apple') # Already added earlier
13
+ False
14
+
15
+ """
16
+
17
+ def __init__(self, dictionary):
18
+ self._dictionary = dictionary
19
+
20
+ def add(self, key) -> bool:
21
+ """
22
+ Adds key to set of A.
23
+
24
+ Returns true if key was not yet in the set.
25
+ """
26
+ visited = self._dictionary.setdefault(key, [False])
27
+ if visited[0]:
28
+ return False
29
+ visited[0] = True
30
+ return True
31
+
32
+ class DictBasedProductSet:
33
+ """
34
+ This class can be constructed from a dictionary with keys in A.
35
+
36
+ The resulting object is a set of AxB.
37
+
38
+ Can be combined with RealHashDict or QuotientDict.
39
+
40
+ >>> fruit_number_set = DictBasedProductSet(dict())
41
+ >>> fruit_number_set.add('Apple', 1)
42
+ True
43
+ >>> fruit_number_set.add('Banana', 1)
44
+ True
45
+ >>> fruit_number_set.add('Apple', 2)
46
+ True
47
+ >>> fruit_number_set.add('Apple', 1) # Already added earlier
48
+ False
49
+
50
+ """
51
+
52
+ def __init__(self, dictionary):
53
+ self._dictionary = dictionary
54
+
55
+ def add(self, key, element) -> bool:
56
+ """
57
+ Adds (key, element) in AxB to set.
58
+
59
+ Returns true if (key, element) was not yet in the set.
60
+ """
61
+
62
+ elements = self._get_elements_for_key(key)
63
+ if element in elements:
64
+ return False
65
+ else:
66
+ elements.add(element)
67
+ return True
68
+
69
+ def _get_elements_for_key(self, key):
70
+ """
71
+ Could be used for potential future optimization:
72
+ When going to a neighboring tetrahedron paired through
73
+ a trivial face-pairing matrix (so it is a tetrahedron within
74
+ the same copy of the fundamental polyhedron), we can keep
75
+ a reference to the set returned by _get_elements_for_key
76
+ and just add the neighboring tetrahedron to this set rather
77
+ than doing the look-up from scratch.
78
+ """
79
+ return self._dictionary.setdefault(key, set())