#include <iostream>
#include <cmath>
using namespace std;
class Point {
public:
double x, y;
double calculate() const {
return pow(x, 3) + pow(y, 2) - 6 * x * y - 39 * x + 18 * y + 20;
}
void print() const {
cout << "F(" << x << ";" << y << ")= " << calculate() << endl;
}
Point copy() const {
return *this;
}
};
int* determine_direction(Point& point, double step_size) {
static int directions[2] = { 0, 0 };
Point left_point = point.copy(), right_point = point.copy();
double initial_value = point.calculate();
left_point.x -= step_size;
right_point.x += step_size;
double left_value = left_point.calculate();
double right_value = right_point.calculate();
left_point.print();
right_point.print();
if (initial_value > left_value || initial_value > right_value) {
if (left_value < right_value) {
directions[0] = -1;
point.x -= step_size;
}
else {
directions[0] = 1;
point.x += step_size;
}
}
else {
directions[0] = 0;
}
left_point = point.copy(); right_point = point.copy();
left_point.y -= step_size;
right_point.y += step_size;
double down_value = left_point.calculate();
double up_value = right_point.calculate();
left_point.print();
right_point.print();
if (initial_value > down_value || initial_value > up_value) {
if (down_value < up_value) {
directions[1] = -1;
point.y -= step_size;
}
else {
directions[1] = 1;
point.y += step_size;
}
}
else {
directions[1] = 0;
}
return directions;
}
void optimize_point(Point& point, double epsilon, double step_size) {
int iteration = 0;
Point last_point;
while (true) {
iteration++;
cout << "Iteration " << iteration << "\nStep size: " << step_size << endl;
cout << "Current Point: ";
point.print();
cout << " -- Find direction -- " << endl;
last_point = point.copy();
int* directions = determine_direction(point, step_size);
if (last_point.calculate() > point.calculate()) {
cout << " -- Pattern movement -- "<< endl;
while (last_point.calculate() >= point.calculate()) {
last_point = point.copy();
point.x += directions[0] * step_size;
point.y += directions[1] * step_size;
point.print();
}
point = last_point.copy();
cout << " -- New Base Point -- " << endl;
point.print();
}
else if (step_size >= epsilon) {
cout << " -- Change step -- " << endl;
step_size /= 2;
}
else {
break;
}
cout << endl;
}
cout << "\nFinal Result:\nAchieved within " << iteration << " iterations with epsilon precision at:\n";
point.print();
}
int main() {
double epsilon, step_size, x, y;
cout << "Enter epsilon value: ";
cin >> epsilon;
if (epsilon <= 0 || epsilon > 1) {
cout << "Invalid epsilon value" << endl;
return 1;
}
cout << "Enter step size: ";
cin >> step_size;
if (step_size <= 0) {
cout << "Invalid step size" << endl;
return 1;
}
cout << "Enter initial x coordinate: ";
cin >> x;
cout << "Enter initial y coordinate: ";
cin >> y;
cout << endl;
Point point;
point.x = x;
point.y = y;
optimize_point(point, epsilon, step_size);
return 0;
}