openscvx 0.4.1.dev43__tar.gz → 0.4.1.dev61__tar.gz

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 (308) hide show
  1. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/.github/workflows/_docs.yml +1 -1
  2. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/.github/workflows/lint.yml +1 -1
  3. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/.github/workflows/tests-integration.yml +1 -1
  4. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/.github/workflows/tests-unit.yml +1 -1
  5. {openscvx-0.4.1.dev43/openscvx.egg-info → openscvx-0.4.1.dev61}/PKG-INFO +1 -1
  6. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/__init__.py +1 -1
  7. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/_version.py +3 -3
  8. openscvx-0.4.1.dev61/openscvx/algorithms/AugmentedLagrangian.py +227 -0
  9. openscvx-0.4.1.dev61/openscvx/algorithms/ConstantProximalWeight.py +58 -0
  10. openscvx-0.4.1.dev61/openscvx/algorithms/RampProximalWeight.py +72 -0
  11. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/algorithms/__init__.py +4 -7
  12. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/algorithms/base.py +141 -4
  13. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/algorithms/penalized_trust_region.py +3 -2
  14. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/config.py +5 -7
  15. openscvx-0.4.1.dev61/openscvx/discretization/__init__.py +25 -0
  16. openscvx-0.4.1.dev61/openscvx/discretization/base.py +113 -0
  17. openscvx-0.4.1.dev61/openscvx/discretization/linearize_discretize.py +324 -0
  18. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/expert/lowering.py +7 -25
  19. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/lowered/dynamics.py +6 -0
  20. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/lowered/problem.py +0 -1
  21. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/problem.py +17 -15
  22. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/solvers/base.py +9 -9
  23. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lower.py +5 -9
  24. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61/openscvx.egg-info}/PKG-INFO +1 -1
  25. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx.egg-info/SOURCES.txt +5 -2
  26. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/test_autotuning.py +12 -6
  27. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/test_discretization.py +9 -12
  28. openscvx-0.4.1.dev43/openscvx/algorithms/autotuning.py +0 -467
  29. openscvx-0.4.1.dev43/openscvx/discretization/__init__.py +0 -47
  30. openscvx-0.4.1.dev43/openscvx/discretization/discretization.py +0 -257
  31. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/.github/assets/logo.svg +0 -0
  32. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/.github/release-drafter.yml +0 -0
  33. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/.github/workflows/branch-name.yml +0 -0
  34. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/.github/workflows/docs.yml +0 -0
  35. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/.github/workflows/nightly.yml +0 -0
  36. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/.github/workflows/release-drafter.yml +0 -0
  37. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/.github/workflows/release.yml +0 -0
  38. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/.gitignore +0 -0
  39. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/CONTRIBUTING.md +0 -0
  40. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/LICENSE +0 -0
  41. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/README.md +0 -0
  42. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/Foundations/constraint_reformulation.md +0 -0
  43. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/Foundations/control_parameterization.md +0 -0
  44. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/Foundations/discretization.md +0 -0
  45. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/Foundations/ocp.md +0 -0
  46. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/Foundations/scvx.md +0 -0
  47. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/Foundations/time_dilation.md +0 -0
  48. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/UnderTheHood/lowering_architecture.md +0 -0
  49. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/UnderTheHood/vectorization_and_vmapping.md +0 -0
  50. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/UsersGuide/00_introduction.md +0 -0
  51. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/UsersGuide/01_hello_world_brachistochrone.md +0 -0
  52. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/UsersGuide/02_drone_racing_constraints.md +0 -0
  53. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/UsersGuide/03_obstacle_avoidance_vmap.md +0 -0
  54. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/UsersGuide/04_viewpoint_constraints.md +0 -0
  55. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/UsersGuide/05_visualization.md +0 -0
  56. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/UsersGuide/06_logic.md +0 -0
  57. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/UsersGuide/07_lie.md +0 -0
  58. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/assets/favicon.png +0 -0
  59. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/assets/images/ct-scvx_dark.png +0 -0
  60. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/assets/images/ct-scvx_light.png +0 -0
  61. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/assets/images/ctcs_dark.png +0 -0
  62. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/assets/images/ctcs_light.png +0 -0
  63. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/assets/images/problem_class_dark.png +0 -0
  64. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/assets/images/problem_class_light.png +0 -0
  65. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/assets/logo.svg +0 -0
  66. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/citation.md +0 -0
  67. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/examples.md +0 -0
  68. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/getting-started.md +0 -0
  69. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/index.md +0 -0
  70. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/docs/javascripts/mathjax.js +0 -0
  71. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/abstract/brachistochrone.py +0 -0
  72. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/arm/three_link_arm.py +0 -0
  73. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/car/dubins_car.py +0 -0
  74. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/car/dubins_car_conditional.py +0 -0
  75. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/car/dubins_car_disjoint.py +0 -0
  76. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/car/dubins_car_stljax.py +0 -0
  77. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/drone/cinema_vp.py +0 -0
  78. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/drone/dr_double_integrator.py +0 -0
  79. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/drone/dr_vp.py +0 -0
  80. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/drone/dr_vp_nodal.py +0 -0
  81. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/drone/dr_vp_polytope.py +0 -0
  82. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/drone/drone_racing.py +0 -0
  83. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/drone/logo.py +0 -0
  84. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/drone/logo_utils/acl_logo.svg +0 -0
  85. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/drone/logo_utils/svg_path_utils.py +0 -0
  86. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/drone/obstacle_avoidance.py +0 -0
  87. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/drone/obstacle_avoidance_nodal.py +0 -0
  88. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/drone/obstacle_avoidance_vmap.py +0 -0
  89. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/plotting.py +0 -0
  90. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/plotting_viser.py +0 -0
  91. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/realtime/base_problems/cinema_vp_realtime_base.py +0 -0
  92. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/realtime/base_problems/drone_racing_realtime_base.py +0 -0
  93. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/realtime/base_problems/obstacle_avoidance_realtime_base.py +0 -0
  94. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/realtime/cinema_vp_realtime.py +0 -0
  95. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/realtime/drone_racing_realtime.py +0 -0
  96. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/realtime/dubins_car_realtime.py +0 -0
  97. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/realtime/obstacle_avoidance_realtime.py +0 -0
  98. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/rocket/3DoF_pdg.py +0 -0
  99. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/examples/spacecraft/proxops_cw.py +0 -0
  100. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/figures/ctlos_cine.gif +0 -0
  101. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/figures/ctlos_dr.gif +0 -0
  102. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/figures/dtlos_cine.gif +0 -0
  103. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/figures/dtlos_dr.gif +0 -0
  104. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/figures/openscvx_logo.svg +0 -0
  105. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/figures/openscvx_logo_square.png +0 -0
  106. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/figures/oscvx_structure_full_dark.svg +0 -0
  107. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/figures/video_preview.png +0 -0
  108. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/__init__.py +0 -0
  109. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/1-background.avif +0 -0
  110. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/1-background@1x.avif +0 -0
  111. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/1-background@2x.avif +0 -0
  112. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/1-background@3x.avif +0 -0
  113. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/1-background@4x.avif +0 -0
  114. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/2-mars.avif +0 -0
  115. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/2-mars@1x.avif +0 -0
  116. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/2-mars@2x.avif +0 -0
  117. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/2-mars@3x.avif +0 -0
  118. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/2-mars@4x.avif +0 -0
  119. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/3-moon.avif +0 -0
  120. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/3-moon@1x.avif +0 -0
  121. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/3-moon@2x.avif +0 -0
  122. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/3-moon@3x.avif +0 -0
  123. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/3-moon@4x.avif +0 -0
  124. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/4-sat1.avif +0 -0
  125. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/4-sat1@1x.avif +0 -0
  126. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/4-sat1@2x.avif +0 -0
  127. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/4-sat1@3x.avif +0 -0
  128. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/4-sat1@4x.avif +0 -0
  129. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/5-space.avif +0 -0
  130. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/5-space@1x.avif +0 -0
  131. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/5-space@2x.avif +0 -0
  132. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/5-space@3x.avif +0 -0
  133. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/5-space@4x.avif +0 -0
  134. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/6-earth.avif +0 -0
  135. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/6-earth@1x.avif +0 -0
  136. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/6-earth@2x.avif +0 -0
  137. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/6-earth@3x.avif +0 -0
  138. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/images/layers/6-earth@4x.avif +0 -0
  139. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/javascripts/parallax.js +0 -0
  140. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/logo.svg +0 -0
  141. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/stylesheets/custom.css +0 -0
  142. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/assets/stylesheets/parallax.css +0 -0
  143. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/home.html +0 -0
  144. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/main.html +0 -0
  145. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/partials/parallax/hero.html +0 -0
  146. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/material/overrides/partials/parallax.html +0 -0
  147. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/mkdocs.yml +0 -0
  148. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/__main__.py +0 -0
  149. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/algorithms/optimization_results.py +0 -0
  150. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/expert/__init__.py +0 -0
  151. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/expert/byof.py +0 -0
  152. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/expert/validation.py +0 -0
  153. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/init/__init__.py +0 -0
  154. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/init/interpolation.py +0 -0
  155. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/integrators/__init__.py +0 -0
  156. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/integrators/runge_kutta.py +0 -0
  157. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/loader.py +0 -0
  158. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/lowered/__init__.py +0 -0
  159. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/lowered/cvxpy_constraints.py +0 -0
  160. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/lowered/cvxpy_variables.py +0 -0
  161. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/lowered/jax_constraints.py +0 -0
  162. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/lowered/parameters.py +0 -0
  163. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/lowered/unified.py +0 -0
  164. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/plotting/__init__.py +0 -0
  165. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/plotting/plotting.py +0 -0
  166. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/plotting/scp_iteration.py +0 -0
  167. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/plotting/viser/__init__.py +0 -0
  168. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/plotting/viser/animated.py +0 -0
  169. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/plotting/viser/plotly_integration.py +0 -0
  170. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/plotting/viser/primitives.py +0 -0
  171. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/plotting/viser/scp.py +0 -0
  172. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/plotting/viser/server.py +0 -0
  173. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/propagation/__init__.py +0 -0
  174. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/propagation/post_processing.py +0 -0
  175. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/propagation/propagation.py +0 -0
  176. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/solvers/__init__.py +0 -0
  177. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/solvers/ptr_solver.py +0 -0
  178. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/__init__.py +0 -0
  179. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/augmentation.py +0 -0
  180. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/builder.py +0 -0
  181. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/constraint_set.py +0 -0
  182. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/expr/__init__.py +0 -0
  183. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/expr/arithmetic.py +0 -0
  184. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/expr/array.py +0 -0
  185. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/expr/constraint.py +0 -0
  186. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/expr/control.py +0 -0
  187. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/expr/expr.py +0 -0
  188. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/expr/lie/__init__.py +0 -0
  189. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/expr/lie/adjoint.py +0 -0
  190. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/expr/lie/se3.py +0 -0
  191. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/expr/lie/so3.py +0 -0
  192. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/expr/linalg.py +0 -0
  193. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/expr/logic.py +0 -0
  194. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/expr/math.py +0 -0
  195. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/expr/spatial.py +0 -0
  196. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/expr/state.py +0 -0
  197. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/expr/stl.py +0 -0
  198. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/expr/variable.py +0 -0
  199. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/expr/vmap.py +0 -0
  200. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/hashing.py +0 -0
  201. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/__init__.py +0 -0
  202. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/cvxpy/__init__.py +0 -0
  203. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/cvxpy/_lowerer.py +0 -0
  204. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/cvxpy/_registry.py +0 -0
  205. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/cvxpy/arithmetic.py +0 -0
  206. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/cvxpy/array.py +0 -0
  207. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/cvxpy/constraint.py +0 -0
  208. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/cvxpy/control.py +0 -0
  209. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/cvxpy/expr.py +0 -0
  210. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/cvxpy/linalg.py +0 -0
  211. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/cvxpy/logic.py +0 -0
  212. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/cvxpy/math.py +0 -0
  213. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/cvxpy/state.py +0 -0
  214. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/jax/__init__.py +0 -0
  215. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/jax/_lowerer.py +0 -0
  216. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/jax/_registry.py +0 -0
  217. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/jax/arithmetic.py +0 -0
  218. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/jax/array.py +0 -0
  219. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/jax/constraint.py +0 -0
  220. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/jax/control.py +0 -0
  221. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/jax/expr.py +0 -0
  222. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/jax/lie.py +0 -0
  223. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/jax/linalg.py +0 -0
  224. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/jax/logic.py +0 -0
  225. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/jax/math.py +0 -0
  226. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/jax/spatial.py +0 -0
  227. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/jax/state.py +0 -0
  228. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/jax/stl.py +0 -0
  229. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/lowerers/jax/vmap.py +0 -0
  230. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/parser/__init__.py +0 -0
  231. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/parser/_registry.py +0 -0
  232. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/parser/array.py +0 -0
  233. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/parser/constraint.py +0 -0
  234. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/parser/lie.py +0 -0
  235. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/parser/linalg.py +0 -0
  236. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/parser/logic.py +0 -0
  237. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/parser/math.py +0 -0
  238. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/parser/parser.py +0 -0
  239. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/parser/spatial.py +0 -0
  240. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/parser/stl.py +0 -0
  241. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/parser/tokenizer.py +0 -0
  242. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/preprocessing.py +0 -0
  243. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/problem.py +0 -0
  244. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/time.py +0 -0
  245. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/symbolic/unified.py +0 -0
  246. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/utils/__init__.py +0 -0
  247. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/utils/cache.py +0 -0
  248. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/utils/caching.py +0 -0
  249. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/utils/printing.py +0 -0
  250. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/utils/profiling.py +0 -0
  251. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx/utils/utils.py +0 -0
  252. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx.egg-info/dependency_links.txt +0 -0
  253. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx.egg-info/entry_points.txt +0 -0
  254. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx.egg-info/requires.txt +0 -0
  255. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/openscvx.egg-info/top_level.txt +0 -0
  256. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/pyproject.toml +0 -0
  257. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/scripts/gen_example_pages.py +0 -0
  258. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/scripts/gen_ref_pages.py +0 -0
  259. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/setup.cfg +0 -0
  260. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/__init__.py +0 -0
  261. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/brachistochrone_analytical.py +0 -0
  262. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/fixtures/brachistochrone.json +0 -0
  263. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/fixtures/brachistochrone.yaml +0 -0
  264. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/__init__.py +0 -0
  265. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/expr/__init__.py +0 -0
  266. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/expr/test_arithmetic.py +0 -0
  267. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/expr/test_array.py +0 -0
  268. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/expr/test_constraint.py +0 -0
  269. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/expr/test_expr.py +0 -0
  270. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/expr/test_lie.py +0 -0
  271. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/expr/test_linalg.py +0 -0
  272. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/expr/test_logic.py +0 -0
  273. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/expr/test_math.py +0 -0
  274. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/expr/test_node_reference.py +0 -0
  275. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/expr/test_parameters.py +0 -0
  276. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/expr/test_scaling.py +0 -0
  277. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/expr/test_spatial.py +0 -0
  278. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/expr/test_variable.py +0 -0
  279. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/expr/test_vmap.py +0 -0
  280. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/parser/__init__.py +0 -0
  281. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/parser/test_array.py +0 -0
  282. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/parser/test_constraint.py +0 -0
  283. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/parser/test_lie.py +0 -0
  284. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/parser/test_linalg.py +0 -0
  285. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/parser/test_load.py +0 -0
  286. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/parser/test_logic.py +0 -0
  287. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/parser/test_math.py +0 -0
  288. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/parser/test_parser.py +0 -0
  289. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/parser/test_spatial.py +0 -0
  290. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/parser/test_stl.py +0 -0
  291. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/parser/test_tokenizer.py +0 -0
  292. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/parser/test_vmap.py +0 -0
  293. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/test_augmentation.py +0 -0
  294. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/test_hashing.py +0 -0
  295. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/test_lower_cvxpy.py +0 -0
  296. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/test_lower_jax.py +0 -0
  297. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/test_preprocessing.py +0 -0
  298. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/symbolic/test_unified.py +0 -0
  299. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/test_brachistochrone.py +0 -0
  300. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/test_cvxpygen_optional.py +0 -0
  301. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/test_examples.py +0 -0
  302. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/test_expert.py +0 -0
  303. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/test_init.py +0 -0
  304. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/test_integrators.py +0 -0
  305. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/test_loader.py +0 -0
  306. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/test_optimization_results.py +0 -0
  307. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/test_plotting.py +0 -0
  308. {openscvx-0.4.1.dev43 → openscvx-0.4.1.dev61}/tests/test_propagation.py +0 -0
@@ -28,7 +28,7 @@ jobs:
28
28
  - name: Set up Python
29
29
  uses: actions/setup-python@v5
30
30
  with:
31
- python-version: '3.13'
31
+ python-version: '3.14'
32
32
 
33
33
  - name: Install uv
34
34
  uses: astral-sh/setup-uv@v7
@@ -19,7 +19,7 @@ jobs:
19
19
  - name: Set up Python
20
20
  uses: actions/setup-python@v5
21
21
  with:
22
- python-version: '3.13'
22
+ python-version: '3.14'
23
23
 
24
24
  - name: Install uv
25
25
  uses: astral-sh/setup-uv@v7
@@ -17,7 +17,7 @@ jobs:
17
17
  fail-fast: false # Continue testing other examples even if one fails
18
18
  matrix:
19
19
  os: [ubuntu-latest, macos-latest]
20
- python-version: ['3.11', '3.12', '3.13']
20
+ python-version: ['3.11', '3.12', '3.13', '3.14']
21
21
 
22
22
  steps:
23
23
  - name: Checkout repository
@@ -18,7 +18,7 @@ jobs:
18
18
  fail-fast: false # Continue testing other versions even if one fails
19
19
  matrix:
20
20
  os: [ubuntu-latest, macos-latest]
21
- python-version: ['3.11', '3.12', '3.13']
21
+ python-version: ['3.11', '3.12', '3.13', '3.14']
22
22
 
23
23
  steps:
24
24
  - name: Checkout repository
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: openscvx
3
- Version: 0.4.1.dev43
3
+ Version: 0.4.1.dev61
4
4
  Summary: A general Python-based successive convexification implementation which uses a JAX backend.
5
5
  Author-email: Chris Hayner and Griffin Norris <haynec@uw.edu>
6
6
  License: Apache Software License
@@ -10,7 +10,7 @@ import openscvx.symbolic.expr.lie as lie
10
10
  import openscvx.symbolic.expr.linalg as linalg
11
11
  import openscvx.symbolic.expr.spatial as spatial
12
12
  import openscvx.symbolic.expr.stl as stl
13
- from openscvx.algorithms.autotuning import (
13
+ from openscvx.algorithms import (
14
14
  AugmentedLagrangian,
15
15
  ConstantProximalWeight,
16
16
  RampProximalWeight,
@@ -28,7 +28,7 @@ version_tuple: VERSION_TUPLE
28
28
  commit_id: COMMIT_ID
29
29
  __commit_id__: COMMIT_ID
30
30
 
31
- __version__ = version = '0.4.1.dev43'
32
- __version_tuple__ = version_tuple = (0, 4, 1, 'dev43')
31
+ __version__ = version = '0.4.1.dev61'
32
+ __version_tuple__ = version_tuple = (0, 4, 1, 'dev61')
33
33
 
34
- __commit_id__ = commit_id = 'g876c409c7'
34
+ __commit_id__ = commit_id = 'gf97d8cf97'
@@ -0,0 +1,227 @@
1
+ """Autotuning functions for SCP (Successive Convex Programming) parameters."""
2
+
3
+ from copy import deepcopy
4
+ from typing import TYPE_CHECKING, List
5
+
6
+ import numpy as np
7
+
8
+ from openscvx.config import Config
9
+ from openscvx.utils.printing import (
10
+ Column,
11
+ Verbosity,
12
+ color_acceptance_ratio,
13
+ color_adaptive_state,
14
+ color_J_nonlin,
15
+ )
16
+
17
+ from .base import AutotuningBase
18
+
19
+ if TYPE_CHECKING:
20
+ from openscvx.lowered import LoweredJaxConstraints
21
+
22
+ from .base import AlgorithmState, CandidateIterate
23
+
24
+
25
+ class AugmentedLagrangian(AutotuningBase):
26
+ """Augmented Lagrangian method for autotuning SCP weights.
27
+
28
+ This method uses Lagrange multipliers and penalty parameters to handle
29
+ constraints. The method:
30
+ - Updates Lagrange multipliers based on constraint violations
31
+ - Increases penalty parameters when constraints are violated
32
+ - Decreases penalty parameters when constraints are satisfied
33
+ """
34
+
35
+ COLUMNS: List[Column] = [
36
+ Column("J_nonlin", "J_nonlin", 8, "{: .1e}", color_J_nonlin, Verbosity.STANDARD),
37
+ Column("J_lin", "J_lin", 8, "{: .1e}", color_J_nonlin, Verbosity.STANDARD),
38
+ Column("pred_reduction", "pred_red", 9, "{: .1e}", min_verbosity=Verbosity.FULL),
39
+ Column("actual_reduction", "act_red", 9, "{: .1e}", min_verbosity=Verbosity.FULL),
40
+ Column(
41
+ "acceptance_ratio",
42
+ "acc_ratio",
43
+ 9,
44
+ "{: .2e}",
45
+ color_acceptance_ratio,
46
+ Verbosity.STANDARD,
47
+ ),
48
+ Column("lam_prox", "lam_prox", 8, "{: .1e}", min_verbosity=Verbosity.FULL),
49
+ Column("adaptive_state", "Adaptive", 16, "{}", color_adaptive_state, Verbosity.FULL),
50
+ ]
51
+
52
+ def __init__(
53
+ self,
54
+ rho_init: float = 1.0,
55
+ rho_max: float = 1e6,
56
+ gamma_1: float = 2.0,
57
+ gamma_2: float = 0.5,
58
+ eta_0: float = 1e-2,
59
+ eta_1: float = 1e-1,
60
+ eta_2: float = 0.8,
61
+ ep: float = 0.5,
62
+ eta_lambda: float = 1e0,
63
+ lam_vc_max: float = 1e5,
64
+ lam_prox_min: float = 1e-3,
65
+ lam_prox_max: float = 2e5,
66
+ lam_cost_drop: int = -1,
67
+ lam_cost_relax: float = 1.0,
68
+ ):
69
+ """Initialize Augmented Lagrangian autotuning parameters.
70
+
71
+ All parameters have defaults and can be modified after instantiation
72
+ via attribute access (e.g., ``autotuner.rho_max = 1e7``).
73
+
74
+ Args:
75
+ rho_init: Initial penalty parameter for constraints. Defaults to 1.0.
76
+ rho_max: Maximum penalty parameter. Defaults to 1e6.
77
+ gamma_1: Factor to increase trust region weight when ratio is low.
78
+ Defaults to 2.0.
79
+ gamma_2: Factor to decrease trust region weight when ratio is high.
80
+ Defaults to 0.5.
81
+ eta_0: Acceptance ratio threshold below which solution is rejected.
82
+ Defaults to 1e-2.
83
+ eta_1: Threshold above which solution is accepted with constant weight.
84
+ Defaults to 1e-1.
85
+ eta_2: Threshold above which solution is accepted with lower weight.
86
+ Defaults to 0.8.
87
+ ep: Threshold for virtual control weight update (nu > ep vs nu <= ep).
88
+ Defaults to 0.5.
89
+ eta_lambda: Step size for virtual control weight update. Defaults to 1e0.
90
+ lam_vc_max: Maximum virtual control penalty weight. Defaults to 1e5.
91
+ lam_prox_min: Minimum trust region (proximal) weight. Defaults to 1e-3.
92
+ lam_prox_max: Maximum trust region (proximal) weight. Defaults to 2e5.
93
+ lam_cost_drop: Iteration after which cost relaxation applies (-1 = never).
94
+ Defaults to -1.
95
+ lam_cost_relax: Factor applied to lam_cost after lam_cost_drop.
96
+ Defaults to 1.0.
97
+ """
98
+ self.rho_init = rho_init
99
+ self.rho_max = rho_max
100
+ self.gamma_1 = gamma_1
101
+ self.gamma_2 = gamma_2
102
+ self.eta_0 = eta_0
103
+ self.eta_1 = eta_1
104
+ self.eta_2 = eta_2
105
+ self.ep = ep
106
+ self.eta_lambda = eta_lambda
107
+ self.lam_vc_max = lam_vc_max
108
+ self.lam_prox_min = lam_prox_min
109
+ self.lam_prox_max = lam_prox_max
110
+ self.lam_cost_drop = lam_cost_drop
111
+ self.lam_cost_relax = lam_cost_relax
112
+
113
+ def update_weights(
114
+ self,
115
+ state: "AlgorithmState",
116
+ candidate: "CandidateIterate",
117
+ nodal_constraints: "LoweredJaxConstraints",
118
+ settings: Config,
119
+ params: dict,
120
+ ) -> str:
121
+ """Update SCP weights and cost parameters based on iteration number.
122
+
123
+ Args:
124
+ state: Solver state containing current weight values (mutated in place)
125
+ nodal_constraints: Lowered JAX constraints
126
+ settings: Configuration object containing adaptation parameters
127
+ params: Dictionary of problem parameters
128
+ """
129
+ # Calculate nonlinear penalty for current candidate
130
+ nonlinear_cost, nonlinear_penalty, nodal_penalty = self.calculate_nonlinear_penalty(
131
+ candidate.x_prop,
132
+ candidate.x,
133
+ candidate.u,
134
+ state.lam_vc,
135
+ state.lam_vb,
136
+ state.lam_cost,
137
+ nodal_constraints,
138
+ params,
139
+ settings,
140
+ )
141
+
142
+ candidate.J_nonlin = nonlinear_cost + nonlinear_penalty + nodal_penalty
143
+
144
+ # Update cost relaxation parameter after cost_drop iterations
145
+ if state.k > self.lam_cost_drop:
146
+ candidate.lam_cost = state.lam_cost * self.lam_cost_relax
147
+ else:
148
+ candidate.lam_cost = settings.scp.lam_cost
149
+
150
+ lam_prox_k = deepcopy(state.lam_prox)
151
+
152
+ if state.k > 1:
153
+ prev_nonlinear_cost, prev_nonlinear_penalty, prev_nodal_penalty = (
154
+ self.calculate_nonlinear_penalty(
155
+ state.x_prop(),
156
+ state.x,
157
+ state.u,
158
+ state.lam_vc,
159
+ state.lam_vb,
160
+ state.lam_cost,
161
+ nodal_constraints,
162
+ params,
163
+ settings,
164
+ )
165
+ )
166
+
167
+ J_nonlin_prev = prev_nonlinear_cost + prev_nonlinear_penalty + prev_nodal_penalty
168
+
169
+ actual_reduction = J_nonlin_prev - candidate.J_nonlin
170
+ predicted_reduction = J_nonlin_prev - candidate.J_lin
171
+
172
+ if predicted_reduction == 0:
173
+ raise ValueError("Predicted reduction is 0.")
174
+
175
+ rho = actual_reduction / predicted_reduction
176
+
177
+ state.pred_reduction_history.append(predicted_reduction)
178
+ state.actual_reduction_history.append(actual_reduction)
179
+ state.acceptance_ratio_history.append(rho)
180
+
181
+ if rho < self.eta_0:
182
+ # Reject Solution and higher weight
183
+ lam_prox_k1 = min(self.lam_prox_max, self.gamma_1 * lam_prox_k)
184
+ state.lam_prox_history.append(lam_prox_k1)
185
+ adaptive_state = "Reject Higher"
186
+ elif rho >= self.eta_0 and rho < self.eta_1:
187
+ # Accept Solution with heigher weight
188
+ lam_prox_k1 = min(self.lam_prox_max, self.gamma_1 * lam_prox_k)
189
+ state.lam_prox_history.append(lam_prox_k1)
190
+ state.accept_solution(candidate)
191
+ adaptive_state = "Accept Higher"
192
+ elif rho >= self.eta_1 and rho < self.eta_2:
193
+ # Accept Solution with constant weight
194
+ lam_prox_k1 = lam_prox_k
195
+ state.lam_prox_history.append(lam_prox_k1)
196
+ state.accept_solution(candidate)
197
+ adaptive_state = "Accept Constant"
198
+ else:
199
+ # Accept Solution with lower weight
200
+ lam_prox_k1 = max(self.lam_prox_min, self.gamma_2 * lam_prox_k)
201
+ state.lam_prox_history.append(lam_prox_k1)
202
+ state.accept_solution(candidate)
203
+ adaptive_state = "Accept Lower"
204
+
205
+ # Update virtual control weight matrix
206
+ nu = (settings.sim.inv_S_x @ abs(candidate.x[1:] - candidate.x_prop).T).T
207
+
208
+ # Vectorized update: use mask to select between two update rules
209
+ mask = nu > self.ep
210
+ # when abs(nu) > ep
211
+ scale = self.eta_lambda * (1 / (2 * state.lam_prox))
212
+ case1 = state.lam_vc + nu * scale
213
+ # when abs(nu) <= ep
214
+ case2 = state.lam_vc + (nu**2) / self.ep * scale
215
+ vc_new = np.where(mask, case1, case2)
216
+ vc_new = np.minimum(self.lam_vc_max, vc_new)
217
+ candidate.lam_vc = vc_new
218
+ candidate.lam_vb = settings.scp.lam_vb
219
+
220
+ else:
221
+ state.lam_prox_history.append(lam_prox_k)
222
+ candidate.lam_vc = settings.scp.lam_vc
223
+ candidate.lam_vb = settings.scp.lam_vb
224
+ state.accept_solution(candidate)
225
+ adaptive_state = "Initial"
226
+
227
+ return adaptive_state
@@ -0,0 +1,58 @@
1
+ """Autotuning functions for SCP (Successive Convex Programming) parameters."""
2
+
3
+ from typing import TYPE_CHECKING
4
+
5
+ from openscvx.config import Config
6
+
7
+ from .base import AutotuningBase
8
+
9
+ if TYPE_CHECKING:
10
+ from openscvx.lowered import LoweredJaxConstraints
11
+
12
+ from .base import AlgorithmState, CandidateIterate
13
+
14
+
15
+ class ConstantProximalWeight(AutotuningBase):
16
+ """Constant Proximal Weight method.
17
+
18
+ This method keeps the trust region weight constant throughout the optimization,
19
+ while still updating virtual control weights and handling cost relaxation.
20
+ Useful when you want a fixed trust region size without adaptation.
21
+ """
22
+
23
+ def __init__(
24
+ self,
25
+ lam_cost_drop: int = -1,
26
+ lam_cost_relax: float = 1.0,
27
+ ):
28
+ self.lam_cost_drop = lam_cost_drop
29
+ self.lam_cost_relax = lam_cost_relax
30
+
31
+ def update_weights(
32
+ self,
33
+ state: "AlgorithmState",
34
+ candidate: "CandidateIterate",
35
+ nodal_constraints: "LoweredJaxConstraints",
36
+ settings: Config,
37
+ params: dict,
38
+ ) -> str:
39
+ """Update SCP weights keeping trust region constant.
40
+
41
+ Args:
42
+ state: Solver state containing current weight values (mutated in place)
43
+ nodal_constraints: Lowered JAX constraints
44
+ settings: Configuration object containing adaptation parameters
45
+ params: Dictionary of problem parameters
46
+
47
+ Returns:
48
+ str: Adaptive state string (e.g., "Accept", "Reject")
49
+ """
50
+ # Update cost relaxation parameter after cost_drop iterations
51
+ if state.k > self.lam_cost_drop:
52
+ candidate.lam_cost = state.lam_cost * self.lam_cost_relax
53
+ else:
54
+ candidate.lam_cost = settings.scp.lam_cost
55
+
56
+ state.lam_prox_history.append(state.lam_prox)
57
+ state.accept_solution(candidate)
58
+ return "Accept Constant"
@@ -0,0 +1,72 @@
1
+ """Autotuning functions for SCP (Successive Convex Programming) parameters."""
2
+
3
+ from typing import TYPE_CHECKING
4
+
5
+ from openscvx.config import Config
6
+
7
+ from .base import AutotuningBase
8
+
9
+ if TYPE_CHECKING:
10
+ from openscvx.lowered import LoweredJaxConstraints
11
+
12
+ from .base import AlgorithmState, CandidateIterate
13
+
14
+
15
+ class RampProximalWeight(AutotuningBase):
16
+ """Ramp Proximal Weight method.
17
+
18
+ This method ramps the proximal weight up linearly over the first few iterations,
19
+ then keeps it constant.
20
+ """
21
+
22
+ def __init__(
23
+ self,
24
+ ramp_factor: float = 1.0,
25
+ lam_prox_max: float = 1e3,
26
+ lam_cost_drop: int = -1,
27
+ lam_cost_relax: float = 1.0,
28
+ ):
29
+ self.ramp_factor = ramp_factor
30
+ self.lam_prox_max = lam_prox_max
31
+ self.lam_cost_drop = lam_cost_drop
32
+ self.lam_cost_relax = lam_cost_relax
33
+
34
+ def update_weights(
35
+ self,
36
+ state: "AlgorithmState",
37
+ candidate: "CandidateIterate",
38
+ nodal_constraints: "LoweredJaxConstraints",
39
+ settings: Config,
40
+ params: dict,
41
+ ) -> str:
42
+ """Update SCP weights keeping trust region constant.
43
+
44
+ Args:
45
+ state: Solver state containing current weight values (mutated in place)
46
+ nodal_constraints: Lowered JAX constraints
47
+ settings: Configuration object containing adaptation parameters
48
+ params: Dictionary of problem parameters
49
+
50
+ Returns:
51
+ str: Adaptive state string (e.g., "Accept", "Reject")
52
+ """
53
+ # Update cost relaxation parameter after cost_drop iterations
54
+ if state.k > self.lam_cost_drop:
55
+ candidate.lam_cost = state.lam_cost * self.lam_cost_relax
56
+ else:
57
+ candidate.lam_cost = settings.scp.lam_cost
58
+
59
+ # Check if we're already at max before updating
60
+ was_at_max = state.lam_prox >= self.lam_prox_max
61
+
62
+ # Calculate and append new value
63
+ new_lam_prox = min(state.lam_prox * self.ramp_factor, self.lam_prox_max)
64
+ state.lam_prox_history.append(new_lam_prox)
65
+
66
+ # If we were already at max, or if we just reached it and it's staying constant
67
+ if was_at_max:
68
+ state.accept_solution(candidate)
69
+ return "Accept Constant"
70
+ else:
71
+ state.accept_solution(candidate)
72
+ return "Accept Higher"
@@ -77,15 +77,12 @@ Current Implementations:
77
77
  - :class:`PenalizedTrustRegion`: Penalized Trust Region (PTR) algorithm
78
78
  """
79
79
 
80
- from .autotuning import (
81
- AugmentedLagrangian,
82
- AutotuningBase,
83
- ConstantProximalWeight,
84
- RampProximalWeight,
85
- )
86
- from .base import Algorithm, AlgorithmState, DiscretizationResult
80
+ from .AugmentedLagrangian import AugmentedLagrangian
81
+ from .base import Algorithm, AlgorithmState, AutotuningBase, DiscretizationResult
82
+ from .ConstantProximalWeight import ConstantProximalWeight
87
83
  from .optimization_results import OptimizationResults
88
84
  from .penalized_trust_region import PenalizedTrustRegion
85
+ from .RampProximalWeight import RampProximalWeight
89
86
 
90
87
  __all__ = [
91
88
  # Base class
@@ -7,10 +7,12 @@ during SCP iterations.
7
7
 
8
8
  from abc import ABC, abstractmethod
9
9
  from dataclasses import dataclass, field
10
- from typing import TYPE_CHECKING, List, Optional, Union
10
+ from typing import TYPE_CHECKING, List, Optional, Tuple, Union
11
11
 
12
12
  import numpy as np
13
13
 
14
+ from openscvx.utils.printing import Column
15
+
14
16
  if TYPE_CHECKING:
15
17
  from openscvx.config import Config
16
18
  from openscvx.lowered.jax_constraints import LoweredJaxConstraints
@@ -63,6 +65,141 @@ class DiscretizationResult:
63
65
  )
64
66
 
65
67
 
68
+ class AutotuningBase(ABC):
69
+ """Base class for autotuning methods in SCP algorithms.
70
+
71
+ This class provides common functionality for calculating costs and penalties
72
+ that are shared across different autotuning strategies (e.g., Penalized Trust
73
+ Region, Augmented Lagrangian).
74
+
75
+ Subclasses should implement the `update_weights` method to define their specific
76
+ weight update strategy.
77
+
78
+ Class Attributes:
79
+ COLUMNS: List of Column specs for autotuner-specific metrics to display.
80
+ Subclasses override this to add their own columns.
81
+ """
82
+
83
+ COLUMNS: List[Column] = []
84
+
85
+ @staticmethod
86
+ def calculate_cost_from_state(x: np.ndarray, settings: "Config") -> float:
87
+ """Calculate cost from state vector based on final_type and initial_type.
88
+
89
+ Args:
90
+ x: State trajectory array (n_nodes, n_states)
91
+ settings: Configuration object containing state types
92
+
93
+ Returns:
94
+ float: Computed cost
95
+ """
96
+ scaled_x = (settings.sim.inv_S_x @ (x.T - settings.sim.c_x[:, None])).T
97
+ cost = 0.0
98
+ for i in range(settings.sim.n_states):
99
+ if settings.sim.x.final_type[i] == "Minimize":
100
+ cost += scaled_x[-1, i]
101
+ if settings.sim.x.final_type[i] == "Maximize":
102
+ cost -= scaled_x[-1, i]
103
+ if settings.sim.x.initial_type[i] == "Minimize":
104
+ cost += scaled_x[0, i]
105
+ if settings.sim.x.initial_type[i] == "Maximize":
106
+ cost -= scaled_x[0, i]
107
+ return cost
108
+
109
+ @staticmethod
110
+ def calculate_nonlinear_penalty(
111
+ x_prop: np.ndarray,
112
+ x_bar: np.ndarray,
113
+ u_bar: np.ndarray,
114
+ lam_vc: np.ndarray,
115
+ lam_vb: float,
116
+ lam_cost: float,
117
+ nodal_constraints: "LoweredJaxConstraints",
118
+ params: dict,
119
+ settings: "Config",
120
+ ) -> Tuple[float, float, float]:
121
+ """Calculate nonlinear penalty components.
122
+
123
+ This method computes three penalty components:
124
+ 1. Cost penalty: weighted original cost
125
+ 2. Virtual control penalty: penalty for dynamics violations
126
+ 3. Nodal penalty: penalty for constraint violations
127
+
128
+ Args:
129
+ x_prop: Propagated state (n_nodes-1, n_states)
130
+ x_bar: Previous iteration state (n_nodes, n_states)
131
+ u_bar: Solution control (n_nodes, n_controls)
132
+ lam_vc: Virtual control weight (scalar or matrix)
133
+ lam_vb: Virtual buffer penalty weight (scalar)
134
+ lam_cost: Cost relaxation parameter (scalar)
135
+ nodal_constraints: Lowered JAX constraints
136
+ params: Dictionary of problem parameters
137
+ settings: Configuration object
138
+
139
+ Returns:
140
+ Tuple of (nonlinear_cost, nonlinear_penalty, nodal_penalty):
141
+ - nonlinear_cost: Weighted cost component
142
+ - nonlinear_penalty: Virtual control penalty
143
+ - nodal_penalty: Constraint violation penalty
144
+ """
145
+ nodal_penalty = 0.0
146
+
147
+ # Evaluate nodal constraints
148
+ for constraint in nodal_constraints.nodal:
149
+ # Nodal constraint function is vmapped: func(x, u, node, params)
150
+ # When called with arrays, it evaluates at all nodes
151
+ g = constraint.func(x_bar, u_bar, 0, params)
152
+ # Only sum violations at nodes where constraint is enforced
153
+ if constraint.nodes is not None:
154
+ # Filter to only specified nodes
155
+ # Convert to numpy array for JAX compatibility
156
+ nodes_array = np.array(constraint.nodes)
157
+ g_filtered = g[nodes_array]
158
+ else:
159
+ # If no nodes specified, check all nodes
160
+ g_filtered = g
161
+ nodal_penalty += lam_vb * np.sum(np.maximum(0, g_filtered))
162
+
163
+ # Evaluate cross-node constraints
164
+ for constraint in nodal_constraints.cross_node:
165
+ # Cross-node constraint function signature: func(X, U, params)
166
+ # No node argument - operates on full trajectory
167
+ g = constraint.func(x_bar, u_bar, params)
168
+ # Cross-node constraints return scalar or array, sum all violations
169
+ nodal_penalty += lam_vb * np.sum(np.maximum(0, g))
170
+
171
+ cost = AutotuningBase.calculate_cost_from_state(x_bar, settings)
172
+ x_diff = settings.sim.inv_S_x @ (x_bar[1:, :] - x_prop).T
173
+
174
+ return lam_cost * cost, np.sum(lam_vc * np.abs(x_diff.T)), nodal_penalty
175
+
176
+ @abstractmethod
177
+ def update_weights(
178
+ self,
179
+ state: "AlgorithmState",
180
+ candidate: "CandidateIterate",
181
+ nodal_constraints: "LoweredJaxConstraints",
182
+ settings: "Config",
183
+ params: dict,
184
+ ) -> str:
185
+ """Update SCP weights and cost parameters based on iteration state.
186
+
187
+ This method is called each iteration to adapt weights based on the
188
+ current solution quality and constraint satisfaction.
189
+
190
+ Args:
191
+ state: Solver state containing current weight values (mutated in place)
192
+ nodal_constraints: Lowered JAX constraints
193
+ settings: Configuration object containing adaptation parameters
194
+ params: Dictionary of problem parameters
195
+
196
+ Returns:
197
+ str: Adaptive state string describing the update action (e.g., "Accept Lower")
198
+ """
199
+
200
+ pass
201
+
202
+
66
203
  @dataclass
67
204
  class AlgorithmState:
68
205
  """Mutable state for SCP iterations.
@@ -418,7 +555,7 @@ class Algorithm(ABC):
418
555
  params: Problem parameters dictionary (for warm-start only)
419
556
  settings: Configuration object (for warm-start only)
420
557
  """
421
- ...
558
+ raise NotImplementedError
422
559
 
423
560
  @abstractmethod
424
561
  def step(
@@ -443,7 +580,7 @@ class Algorithm(ABC):
443
580
  Returns:
444
581
  True if convergence criteria are satisfied, False otherwise.
445
582
  """
446
- ...
583
+ raise NotImplementedError
447
584
 
448
585
  @abstractmethod
449
586
  def citation(self) -> List[str]:
@@ -462,4 +599,4 @@ class Algorithm(ABC):
462
599
  for bibtex in algorithm.citation():
463
600
  print(bibtex)
464
601
  """
465
- ...
602
+ raise NotImplementedError
@@ -21,14 +21,15 @@ from openscvx.utils.printing import (
21
21
  color_prob_stat,
22
22
  )
23
23
 
24
- from .autotuning import ConstantProximalWeight, RampProximalWeight
25
24
  from .base import Algorithm, AlgorithmState, CandidateIterate
25
+ from .ConstantProximalWeight import ConstantProximalWeight
26
+ from .RampProximalWeight import RampProximalWeight
26
27
 
27
28
  if TYPE_CHECKING:
28
29
  from openscvx.lowered import LoweredJaxConstraints
29
30
  from openscvx.solvers import ConvexSolver
30
31
 
31
- from .autotuning import AutotuningBase
32
+ from .base import AutotuningBase
32
33
 
33
34
  warnings.filterwarnings("ignore")
34
35
 
@@ -2,7 +2,7 @@ from dataclasses import dataclass, fields
2
2
  from typing import TYPE_CHECKING, Any, Dict, Optional
3
3
 
4
4
  if TYPE_CHECKING:
5
- from openscvx.algorithms.autotuning import AutotuningBase
5
+ from openscvx.algorithms.base import AutotuningBase
6
6
 
7
7
  import numpy as np
8
8
 
@@ -376,11 +376,9 @@ def _resolve_autotuner(val: Any) -> Any:
376
376
  )
377
377
 
378
378
  if not _AUTOTUNER_MAP:
379
- from openscvx.algorithms.autotuning import (
380
- AugmentedLagrangian,
381
- ConstantProximalWeight,
382
- RampProximalWeight,
383
- )
379
+ from openscvx.algorithms.AugmentedLagrangian import AugmentedLagrangian
380
+ from openscvx.algorithms.ConstantProximalWeight import ConstantProximalWeight
381
+ from openscvx.algorithms.RampProximalWeight import RampProximalWeight
384
382
 
385
383
  for cls in (AugmentedLagrangian, ConstantProximalWeight, RampProximalWeight):
386
384
  _AUTOTUNER_MAP[cls.__name__] = cls
@@ -489,7 +487,7 @@ class ScpConfig:
489
487
  # Local import avoids circular dependency:
490
488
  # - autotuning imports Config
491
489
  # - Config should not eagerly import autotuning at module import time
492
- from openscvx.algorithms.autotuning import AugmentedLagrangian
490
+ from openscvx.algorithms.AugmentedLagrangian import AugmentedLagrangian
493
491
 
494
492
  self._autotuner = AugmentedLagrangian()
495
493
  return self._autotuner