pysr_regression.py 1.9 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667
  1. """This script shows how to fit a symbolic regression model to a 2D dataset.
  2. The dataset is generated from a simple function and some noise is added.
  3. The script then shows the true function and learned function on a 2D grid."""
  4. # Check out the documentation for more information:
  5. # https://astroautomata.com/PySR/
  6. # https://github.com/MilesCranmer/PySR
  7. # install with:
  8. # pip install pysr
  9. #
  10. import numpy as np
  11. from pysr import PySRRegressor
  12. import vedo
  13. model = PySRRegressor(
  14. maxsize=20,
  15. niterations=40, # < Increase me for better results
  16. binary_operators=["+", "*"],
  17. unary_operators=[
  18. "cos",
  19. "exp",
  20. "sin",
  21. "inv(x) = 1/x",
  22. # ^ Custom operator (julia syntax)
  23. ],
  24. extra_sympy_mappings={"inv": lambda x: 1 / x},
  25. # ^ Define operator for SymPy as well
  26. elementwise_loss="loss(prediction, target) = (prediction - target)^2",
  27. # ^ Custom loss function (use julia syntax)
  28. )
  29. def compute_z(X):
  30. return 0.42345 * np.cos(X[:,1]) + 0.1 * X[:,0]**2 - 0.5
  31. X = 2 * np.random.randn(100, 2)
  32. z = compute_z(X)
  33. # add noise to z values to make it more realistic
  34. z += 0.15 * np.random.randn(100)
  35. model.fit(X, z)
  36. print(model)
  37. grid = vedo.Grid(pos=(0,0,0), res=(100,100)).scale(10)
  38. X_grid = grid.points[:, :2] # 2D points on the grid
  39. z_pred = model.predict(X_grid)
  40. grid.points[:, 2] = z_pred
  41. coords = np.c_[X[:,0], X[:,1], z]
  42. # the truth
  43. grid_truth = grid.clone().alpha(0.1).c("black")
  44. z_truth = compute_z(X_grid)
  45. grid_truth.points[:, 2] = z_truth
  46. grid.compute_normals().cmap("ocean", z_pred)
  47. grid.wireframe(False).lw(0).lighting("glossy")
  48. levels = grid.isolines(n=10).color('white')
  49. loss = model.equations_["loss"]
  50. complexity = model.equations_["complexity"]
  51. pts = vedo.Points(coords, r=8, c="k6")
  52. pl = vedo.pyplot.plot(complexity, loss, xtitle="Complexity", ytitle="Loss", c="blue4")
  53. pl = pl.clone2d("bottom-left", size=0.5)
  54. vedo.show(pts, grid, grid_truth, levels, pl, __doc__, axes=1, viewup="z")