input: Write a python function to optimize a given function using gradient descent.
  assert np.isclose(optimize(lambda x: x**2, 5, 0.1, 1000), 0, atol=1e-6)
  assert np.isclose(optimize(lambda x: (x-2)**2, 10, 0.1, 1000), 2, atol=1e-6)
  assert np.isclose(optimize(lambda x: (x+3)**2, -10, 0.1, 1000), -3, atol=1e-6)
output: def optimize(func, initial, learning_rate, iterations):
      x = initial
      for _ in range(iterations):
          gradient = (func(x + 1e-6) - func(x)) / 1e-6
          x -= learning_rate * gradient
      return x