Золотое сечение для 2D и 3D
17.04.2012, 10:47. Показов 1497. Ответов 0
Суть в том что есть некая функция имеющая минимум в некоторой точке w(х,у) для 2D или w(x,y,z) для 3D.
И есть некий отрезок, с началом в точке a(ax,ay) и концом в точке b(bx,by) (для 3D - a(ax,ay,az), b(bx,by,bz)). И я пытаюсь найти точку на этом отрезке, где значение функции будет минимально методом золотого сечения.
сама функция для 2D
Java | 1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
| public static Point2D gld(Point2D a0,Point2D b0,Point2D d,double l)
{
final double alph=0.618;
Elm<Point2D> e;
Point2D a=new Point2D(0,0),//a0.getX(),a0.getY()),
b=new Point2D(b0.getX(),b0.getY()),
g=a.aGrad();
if((abs(g.getX())<=l)&&(abs(g.getY())<=l)) return a;
Point2D lmb=new Point2D(),u=new Point2D(),opt=new Point2D();
double forX,forY;
double beta=atan((d.getY())/d.getX());
double dlt=cos(PI/4.0-beta)/cos(PI/4.0);
Point2D pL=new Point2D(),
pU=new Point2D();
forX=(b.getX()-a.getX());
forY=(b.getY()-a.getY());
System.out.println("dlt="+dlt+"; beta="+beta+"; sin(beta)="+sin(beta)+"; cos(beta)="+cos(beta)+"; cos(dlt)="+cos(dlt));
if(sqrt(pow((b.getX()-a.getX()),2)+pow((b.getY()-a.getY()),2))>l)
{
lmb.setX(a.getX()+(1-alph)*forX);
u.setX(a.getX()+alph*forX);
lmb.setY(a.getY()+(1-alph)*forY);
u.setY(a.getY()+alph*forY);
pL.setX(lmb.getX()*dlt*cos(beta)+a0.getX()*pow(sin(beta),2)-a0.getY()*sin(beta)*cos(beta));
pL.setY(lmb.getY()*dlt*sin(beta)-a0.getX()*sin(beta)*cos(beta)+a0.getY()*pow(cos(beta),2));
pU.setX(u.getX()*dlt*cos(beta)+a0.getX()*pow(sin(beta),2)-a0.getY()*sin(beta)*cos(beta));
pU.setY(u.getY()*dlt*sin(beta)-a0.getX()*sin(beta)*cos(beta)+a0.getY()*pow(cos(beta),2));
}
while(true)
{
if(sqrt(pow((b.getX()-a.getX()),2)+pow((b.getY()-a.getY()),2))<=l)
{
break;
}
if(pL.fnc()>pU.fnc())
{
a.setP(lmb);
lmb.setP(u);
forX=(b.getX()-a.getX());
forY=(b.getY()-a.getY());
u.setX(a.getX()+alph*forX);
u.setY(a.getY()+alph*forY);
pL.setX(lmb.getX()*dlt*cos(beta)+a0.getX()*pow(sin(beta),2)-a0.getY()*sin(beta)*cos(beta));
pL.setY(lmb.getY()*dlt*sin(beta)-a0.getX()*sin(beta)*cos(beta)+a0.getY()*pow(cos(beta),2));
pU.setX(u.getX()*dlt*cos(beta)+a0.getX()*pow(sin(beta),2)-a0.getY()*sin(beta)*cos(beta));
pU.setY(u.getY()*dlt*sin(beta)-a0.getX()*sin(beta)*cos(beta)+a0.getY()*pow(cos(beta),2));
opt.setP(b);
}
else
{
b.setP(u);
u.setP(lmb);
forX=(b.getX()-a.getX());
forY=(b.getY()-a.getY());
lmb.setX(a.getX()+(1-alph)*forX);
lmb.setY(a.getY()+(1-alph)*forY);
pL.setX(lmb.getX()*dlt*cos(beta)+a0.getX()*pow(sin(beta),2)-a0.getY()*sin(beta)*cos(beta));
pL.setY(lmb.getY()*dlt*sin(beta)-a0.getX()*sin(beta)*cos(beta)+a0.getY()*pow(cos(beta),2));
pU.setX(u.getX()*dlt*cos(beta)+a0.getX()*pow(sin(beta),2)-a0.getY()*sin(beta)*cos(beta));
pU.setY(u.getY()*dlt*sin(beta)-a0.getX()*sin(beta)*cos(beta)+a0.getY()*pow(cos(beta),2));
opt.setP(a);
}
System.out.println("a("+a.getX()+";"+a.getY()+") b("+b.getX()+";"+b.getY()+") lmb("+lmb.getX()+";"+lmb.getY()+") u("+u.getX()+";"+u.getY()+") x'="+(a0.getX()*pow(sin(beta),2)-a0.getY()*sin(beta)*cos(beta))+" y'="+(a0.getX()*sin(beta)*cos(beta)+a0.getY()*pow(cos(beta),2)));
}
if(a.equals(a0)) return a;
opt.setX(opt.getX()*dlt*cos(beta)+a0.getX()*pow(sin(beta),2)-a0.getY()*sin(beta)*cos(beta));
opt.setY(opt.getY()*dlt*sin(beta)-a0.getX()*sin(beta)*cos(beta)+a0.getY()*pow(cos(beta),2));
System.out.println("итого ^"+opt.getX()+";"+opt.getY()+"|"+g.getX()+";"+g.getY());
return opt;
} |
|
Функция для 3D
Java | 1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
| public static Point3D gld(Point3D a0,Point3D b0,Point3D d,double l)
{
Point3D a=new Point3D(a0.getX(),a0.getY(),a0.getZ()),b=new Point3D(b0.getX(),b0.getY(),b0.getZ());
Point3D g=a.aGrad();
if((abs(g.getX())<=l)&&(abs(g.getY())<=l)&&(abs(g.getZ())<=l)) return a;
final double alph=0.618;
Point3D lmb=new Point3D(),u=new Point3D(),opt=new Point3D();
double forX,forY,forZ;
double beta=atan(d.getY()/d.getX());
double gmma=atan(d.getZ()/d.getX());
double dlt=cos((PI/(double)4-beta))/cos(PI/(double)4),
dlt0=cos((PI/(double)4-gmma))/cos(PI/(double)4);
Point3D pL=new Point3D(),pU=new Point3D();
forX=(b.getX()-a.getX());
forY=(b.getY()-a.getY());
forZ=(b.getZ()-a.getZ());
if(sqrt(pow((b.getX()-a.getX()),2)+pow((b.getY()-a.getY()),2))>l)
{
lmb.setX(a.getX()+(1-alph)*forX);
u.setX(a.getX()+alph*forX);
lmb.setY(a.getY()+(1-alph)*forY);
u.setY(a.getY()+alph*forY);
lmb.setZ(a.getZ()+(1-alph)*forZ);
u.setZ(a.getZ()+alph*forZ);//*cos(beta)
pL.setX(lmb.getX()*dlt*cos(beta)+a0.getX()*pow(sin(beta),2)-a0.getY()*sin(beta)*cos(beta)-a0.getZ()*sin(gmma)*cos(gmma));
pL.setY(lmb.getY()*dlt*sin(beta)+a0.getY()*pow(cos(beta),2)-a0.getX()*sin(beta)*cos(beta)-a0.getZ()*sin(gmma)*cos(gmma));
pL.setZ(lmb.getZ()*dlt0*sin(gmma)+a0.getZ()*pow(cos(gmma),2)-a0.getX()*sin(gmma)*cos(gmma)-a0.getY()*sin(gmma)*cos(gmma));//-sqrt(pow(a0.getX(),2)+pow(a0.getY(),2))*sin(gmma)*cos(gmma)+a0.getZ()*pow(cos(gmma),2));
pU.setX(u.getX()*dlt*cos(beta)+a0.getX()*pow(sin(beta),2)-a0.getY()*sin(beta)*cos(beta)-a0.getZ()*sin(gmma)*cos(gmma));
pU.setY(u.getY()*dlt*sin(beta)+a0.getY()*pow(cos(beta),2)-a0.getX()*sin(beta)*cos(beta)-a0.getZ()*sin(gmma)*cos(gmma));
pU.setZ(u.getZ()*dlt0*sin(gmma)+a0.getZ()*pow(cos(gmma),2)-a0.getX()*sin(gmma)*cos(gmma)+a0.getY()*sin(gmma)*cos(gmma));//-sqrt(pow(a0.getX(),2)+pow(a0.getY(),2))*sin(gmma)*cos(gmma)+a0.getZ()*pow(cos(gmma),2));
}
while(true)
{
if(pow(pow((b.getX()-a.getX()),2)+pow((b.getY()-a.getY()),2),1.0/3.0)<=l)
{
break;
}
if(pL.fnc()>pU.fnc())
{
a.setP(lmb);
lmb.setP(u);
forX=(b.getX()-a.getX());
forY=(b.getY()-a.getY());
forZ=(b.getZ()-a.getZ());
u.setX(a.getX()+alph*forX);
u.setY(a.getY()+alph*forY);
u.setZ(a.getZ()+alph*forZ);
pL.setX(lmb.getX()*dlt*cos(beta)+a0.getX()*pow(sin(beta),2)-a0.getY()*sin(beta)*cos(beta)-a0.getZ()*sin(gmma)*cos(gmma));
pL.setY(lmb.getY()*dlt*sin(beta)+a0.getY()*pow(cos(beta),2)-a0.getX()*sin(beta)*cos(beta)-a0.getZ()*sin(gmma)*cos(gmma));
pL.setZ(lmb.getZ()*dlt0*sin(gmma)+a0.getZ()*pow(cos(gmma),2)-a0.getX()*sin(gmma)*cos(gmma)-a0.getY()*sin(gmma)*cos(gmma));//-sqrt(pow(a0.getX(),2)+pow(a0.getY(),2))*sin(gmma)*cos(gmma)+a0.getZ()*pow(cos(gmma),2));
pU.setX(u.getX()*dlt*cos(beta)+a0.getX()*pow(sin(beta),2)-a0.getY()*sin(beta)*cos(beta)-a0.getZ()*sin(gmma)*cos(gmma));
pU.setY(u.getY()*dlt*sin(beta)+a0.getY()*pow(cos(beta),2)-a0.getX()*sin(beta)*cos(beta)-a0.getZ()*sin(gmma)*cos(gmma));
pU.setZ(u.getZ()*dlt0*sin(gmma)+a0.getZ()*pow(cos(gmma),2)-a0.getX()*sin(gmma)*cos(gmma)-a0.getY()*sin(gmma)*cos(gmma));//-sqrt(pow(a0.getX(),2)+pow(a0.getY(),2))*sin(gmma)*cos(gmma)+a0.getZ()*pow(cos(gmma),2));
opt.setP(b);
}
else
{
b.setP(u);
u.setP(lmb);
forX=(b.getX()-a.getX());
forY=(b.getY()-a.getY());
forZ=(b.getZ()-a.getZ());
lmb.setX(a.getX()+(1-alph)*forX);
lmb.setY(a.getY()+(1-alph)*forY);
lmb.setZ(a.getZ()+(1-alph)*forZ);
pL.setX(lmb.getX()*dlt*cos(beta)+a0.getX()*pow(sin(beta),2)-a0.getY()*sin(beta)*cos(beta)-a0.getZ()*sin(gmma)*cos(gmma));
pL.setY(lmb.getY()*dlt*sin(beta)+a0.getY()*pow(cos(beta),2)-a0.getX()*sin(beta)*cos(beta)-a0.getZ()*sin(gmma)*cos(gmma));
pL.setZ(lmb.getZ()*dlt0*sin(gmma)+a0.getZ()*pow(cos(gmma),2)-a0.getX()*sin(gmma)*cos(gmma)-a0.getY()*sin(gmma)*cos(gmma));//-sqrt(pow(a0.getX(),2)+pow(a0.getY(),2))*sin(gmma)*cos(gmma)+a0.getZ()*pow(cos(gmma),2));
pU.setX(u.getX()*dlt*cos(beta)+a0.getX()*pow(sin(beta),2)-a0.getY()*sin(beta)*cos(beta)-a0.getZ()*sin(gmma)*cos(gmma));
pU.setY(u.getY()*dlt*sin(beta)+a0.getY()*pow(cos(beta),2)-a0.getX()*sin(beta)*cos(beta)-a0.getZ()*sin(gmma)*cos(gmma));
pU.setZ(u.getZ()*dlt0*sin(gmma)+a0.getZ()*pow(cos(gmma),2)-a0.getX()*sin(gmma)*cos(gmma)-a0.getY()*sin(gmma)*cos(gmma));//-sqrt(pow(a0.getX(),2)+pow(a0.getY(),2))*sin(gmma)*cos(gmma)+a0.getZ()*pow(cos(gmma),2));
opt.setP(a);
}
System.out.println("a("+a.getX()+";"+a.getY()+";"+a.getZ()+") b("+b.getX()+";"+b.getY()+";"+b.getZ()+")| x'="+(a0.getX()*pow(sin(beta),2)-a0.getY()*sin(beta)*cos(beta))+" y'="+(-a0.getX()*sin(beta)*cos(beta)+a0.getY()*pow(cos(beta),2))+"z'="+(-sqrt(pow(pL.getX(),2)+pow(pL.getY(),2))*sin(gmma)*cos(gmma)+a0.getZ()*pow(cos(gmma),2)));
}
if(a.equals(a0)) return a;
opt.setX(opt.getX()*dlt*cos(beta)+a0.getX()*pow(sin(beta),2)-a0.getY()*sin(beta)*cos(beta)-a0.getZ()*sin(gmma)*cos(gmma));//-a0.getZ()*sin(gmma)*cos(gmma);
opt.setY(opt.getY()*dlt*sin(beta)+a0.getY()*pow(cos(beta),2)-a0.getX()*sin(beta)*cos(beta)-a0.getZ()*sin(gmma)*cos(gmma));//-a0.getZ()*sin(gmma));
opt.setZ(opt.getZ()*dlt0*sin(gmma)+a0.getZ()*pow(cos(gmma),2)-a0.getX()*sin(gmma)*cos(gmma)-a0.getY()*sin(gmma)*cos(gmma));//-sqrt(pow(a0.getX(),2)+pow(a0.getY(),2))*sin(gmma)*cos(gmma)+a0.getZ()*pow(cos(gmma),2));
System.out.println("итого ^"+opt.getX()+";"+opt.getY()+";"+opt.getZ()+"|"+g.getX()+";"+g.getY()+";"+g.getZ());
return opt;
} |
|
Они используют классы Point2D и Point3D.
Класс Point2D:
Java | 1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
| import static java.lang.Math.*;
public class Point2D {
public Point2D()
{
this(Double.NaN,Double.NaN);
}
public Point2D(double x, double y)
{
this.x=x;
this.y=y;
}
public void setP(Point2D pt)
{
this.x=pt.getX();
this.y=pt.getY();
}
public void add(Point2D pt)
{
this.x+=pt.getX();
this.y+=pt.getY();
}
public void mult(double n)
{
this.x*=n;
this.y*=n;
}
public boolean equals(Point2D p)
{
return (this.getX()==p.getX())&&(this.getY()==p.getY());
}
public void setX(double x)
{
this.x=x;
}
public void setY(double y)
{
this.y=y;
}
public double getX()
{
return this.x;
}
public double getY()
{
return this.y;
}
public double fnc()
{
return this.getX()+2*pow(this.getY(),2)+exp(pow(this.getX(),2)+pow(this.getY(),2));
//return pow(this.getX()-3,2)+pow(this.getY()-3,2);//pow(this.getX(),2)-6*this.getX()+9+pow(this.getY(),2)-6*this.getY()+9+3;//pow(pt.getX()-1,2)+pow(pt.getY()-3,2);//pt.getX()*pt.getX()-6*pt.getX()+9+pt.getY()*pt.getY()-6*pt.getY()+9+3;
}
public Point2D aGrad()
{
//return new Point2D(-2*this.getX()+6.0,-2*this.getY()+6.0);
return new Point2D(-(exp(pow(this.getX(),2)+pow(this.getY(),2))*2*this.getX()),-(exp(pow(this.getX(),2)+pow(this.getY(),2))*2*this.getY()));
}
private double x=Double.NaN,y=Double.NaN;
} |
|
Класс Point3D:
Java | 1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
| import static java.lang.Math.pow;
import javax.swing.JOptionPane;
public class Point3D {
public Point3D()
{
this(Double.NaN,Double.NaN,Double.NaN);
}
public Point3D(double x, double y, double z)
{
this.x=x;
this.y=y;
this.z=z;
}
public void setP(Point3D pt)
{
this.x=pt.getX();
this.y=pt.getY();
this.z=pt.getZ();
}
public void mult(double n)
{
this.x*=n;
this.y*=n;
this.z*=n;
}
public boolean equals(Point3D p)
{
if(this.getClass()!=p.getClass())
{
JOptionPane.showMessageDialog(null, "Ошибка:несоответствие классов!");
return false;
}
return (this.getX()==p.getX())&&(this.getY()==p.getY())&&(this.z==p.z);
}
public void setX(double x)
{
this.x=x;
}
public void setY(double y)
{
this.y=y;
}
public void setZ(double z)
{
this.z=z;
}
public double getX()
{
return this.x;
}
public double getY()
{
return this.y;
}
public double getZ()
{
return this.z;
}
public double fnc()
{
//return 4*pow(this.getX(),2)+3*pow(this.getY(),2)+pow(this.getZ(),2)-16*this.getX()-4*this.getZ();
return pow(this.getX()-3,2)+pow(this.getY()-3,2)+pow(this.getZ()-3,2);
}
public Point3D aGrad()
{
//return new Point3D(-(8*this.getX()-16),-(6*this.getY()),-(2*this.getZ()-4));
return new Point3D(-(2*this.getX()-6), -(2*this.getY()-6), -(2*this.getZ()-6));
}
public Point3D grad()
{
return new Point3D((8*this.getX()-16),(6*this.getY()),(2*this.getZ()-4));
}
private double x=Double.NaN,y=Double.NaN,z=Double.NaN;
} |
|
Программа корректно работает только в некоторых случаях. В чем может быть моя ошибка?
0
|