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 from math import cos, pi, sin, sqrt
27 from Numeric import Float64, array, dot
28
29 from more_thuente import more_thuente
30
32 print "\n\n\n\n\n\n\n\n\n\n\n\n\t\t<<< Test Functions >>>\n\n\n"
33 print "\nSelect the function to test:"
34 while 1:
35 input = raw_input('> ')
36 valid_functions = ['1', '2', '3', '4', '5', '6']
37 if input in valid_functions:
38 func = int(input)
39 break
40 else:
41 print "Choose a function number between 1 and 6."
42
43 print "\nSelect a0:"
44 while 1:
45 input = raw_input('> ')
46 valid_vals = ['1e-3', '1e-1', '1e1', '1e3']
47 if input in valid_vals:
48 a0 = float(input)
49 break
50 else:
51 print "Choose a0 as one of ['1e-3', '1e-1', '1e1', '1e3']."
52
53 print "Testing line minimiser using test function " + `func`
54 if func == 1:
55 f, df = func1, dfunc1
56 mu, eta = 0.001, 0.1
57 elif func == 2:
58 f, df = func2, dfunc2
59 mu, eta = 0.1, 0.1
60 elif func == 3:
61 f, df = func3, dfunc3
62 mu, eta = 0.1, 0.1
63 elif func == 4:
64 f, df = func456, dfunc456
65 beta1, beta2 = 0.001, 0.001
66 mu, eta = 0.001, 0.001
67 elif func == 5:
68 f, df = func456, dfunc456
69 beta1, beta2 = 0.01, 0.001
70 mu, eta = 0.001, 0.001
71 elif func == 6:
72 f, df = func456, dfunc456
73 beta1, beta2 = 0.001, 0.01
74 mu, eta = 0.001, 0.001
75
76 xk = array([0.0], Float64)
77 pk = array([1.0], Float64)
78 if func >= 4:
79 args = (beta1, beta2)
80 else:
81 args = ()
82 f0 = apply(f, (xk,)+args)
83 g0 = apply(df, (xk,)+args)
84 a = more_thuente(f, df, args, xk, pk, f0, g0, a_init=a0, mu=mu, eta=eta, print_flag=1)
85 print "The minimum is at " + `a`
86
87
88 -def func1(alpha, beta=2.0):
89 """Test function 1.
90
91 From More, J. J., and Thuente, D. J. 1994, Line search algorithms with guaranteed sufficient
92 decrease. ACM Trans. Math. Softw. 20, 286-307.
93
94 The function is:
95 alpha
96 phi(alpha) = - ---------------
97 alpha**2 + beta
98 """
99
100 return - alpha[0]/(alpha[0]**2 + beta)
101
102
104 """Derivative of test function 1.
105
106 From More, J. J., and Thuente, D. J. 1994, Line search algorithms with guaranteed sufficient
107 decrease. ACM Trans. Math. Softw. 20, 286-307.
108
109 The gradient is:
110 2*alpha**2 1
111 phi'(alpha) = -------------------- - ---------------
112 (alpha**2 + beta)**2 alpha**2 + beta
113 """
114
115 temp = array([0.0], Float64)
116 if alpha[0] > 1e90:
117 return temp
118 else:
119 a = 2.0*(alpha[0]**2)/((alpha[0]**2 + beta)**2)
120 b = 1.0/(alpha[0]**2 + beta)
121 temp[0] = a - b
122 return temp
123
124
125 -def func2(alpha, beta=0.004):
126 """Test function 2.
127
128 From More, J. J., and Thuente, D. J. 1994, Line search algorithms with guaranteed sufficient
129 decrease. ACM Trans. Math. Softw. 20, 286-307.
130
131 The function is:
132
133 phi(alpha) = (alpha + beta)**5 - 2(alpha + beta)**4
134 """
135
136 return (alpha[0] + beta)**5 - 2.0*((alpha[0] + beta)**4)
137
138
139 -def dfunc2(alpha, beta=0.004):
140 """Derivative of test function 2.
141
142 From More, J. J., and Thuente, D. J. 1994, Line search algorithms with guaranteed sufficient
143 decrease. ACM Trans. Math. Softw. 20, 286-307.
144
145 The gradient is:
146
147 phi'(alpha) = 5(alpha + beta)**4 - 8(alpha + beta)**3
148 """
149
150 temp = array([0.0], Float64)
151 temp[0] = 5.0*((alpha[0] + beta)**4) - 8.0*((alpha[0] + beta)**3)
152 return temp
153
154
155 -def func3(alpha, beta=0.01, l=39.0):
156 """Test function 3.
157
158 From More, J. J., and Thuente, D. J. 1994, Line search algorithms with guaranteed sufficient
159 decrease. ACM Trans. Math. Softw. 20, 286-307.
160
161 The function is:
162
163 2(1 - beta) / l*pi \
164 phi(alpha) = phi0(alpha) + ----------- . sin | ---- . alpha |
165 l*pi \ 2 /
166
167 where:
168 / 1 - alpha, if alpha <= 1 - beta,
169 |
170 | alpha - 1, if alpha >= 1 + beta,
171 phi0(alpha) = <
172 | 1 1
173 | ------(alpha - 1)**2 + - beta, if alpha in [1 - beta, 1 + beta].
174 \ 2*beta 2
175 """
176
177
178 if alpha[0] <= 1.0 - beta:
179 phi0 = 1.0 - alpha[0]
180 elif alpha[0] >= 1.0 + beta:
181 phi0 = alpha[0] - 1.0
182 else:
183 phi0 = 0.5/beta * (alpha[0] - 1.0)**2 + 0.5*beta
184
185 return phi0 + 2.0*(1.0 - beta)/(l*pi) * sin(0.5 * l * pi * alpha[0])
186
187
188 -def dfunc3(alpha, beta=0.01, l=39.0):
189 """Derivative of test function 3.
190
191 From More, J. J., and Thuente, D. J. 1994, Line search algorithms with guaranteed sufficient
192 decrease. ACM Trans. Math. Softw. 20, 286-307.
193
194 The gradient is:
195 / l*pi \
196 phi(alpha) = phi0'(alpha) + (1 - beta) . cos | ---- . alpha |
197 \ 2 /
198
199 where:
200 / -1, if alpha <= 1 - beta,
201 |
202 | 1, if alpha >= 1 + beta,
203 phi0'(alpha) = <
204 | alpha - 1
205 | ---------, if alpha in [1 - beta, 1 + beta].
206 \ beta
207 """
208
209
210 if alpha[0] <= 1.0 - beta:
211 phi0_prime = -1.0
212 elif alpha[0] >= 1.0 + beta:
213 phi0_prime = 1.0
214 else:
215 phi0_prime = (alpha[0] - 1.0)/beta
216
217 temp = array([0.0], Float64)
218 temp[0] = phi0_prime + (1.0 - beta) * cos(0.5 * l * pi * alpha[0])
219 return temp
220
221
223 """Test functions 4, 5, and 6.
224
225 From More, J. J., and Thuente, D. J. 1994, Line search algorithms with guaranteed sufficient
226 decrease. ACM Trans. Math. Softw. 20, 286-307.
227
228 The function is:
229
230 phi(alpha) = gamma(beta1) * sqrt((1 - alpha)**2 + beta2**2)
231 + gamma(beta2) * sqrt(alpha**2 + beta1**2)
232
233 where:
234 gamma(beta) = sqrt(1 + beta**2) - beta
235 """
236
237 g1 = sqrt(1.0 + beta1**2) - beta1
238 g2 = sqrt(1.0 + beta2**2) - beta2
239 return g1 * sqrt((1.0 - alpha[0])**2 + beta2**2) + g2 * sqrt(alpha[0]**2 + beta1**2)
240
241
243 """Test functions 4, 5, and 6.
244
245 From More, J. J., and Thuente, D. J. 1994, Line search algorithms with guaranteed sufficient
246 decrease. ACM Trans. Math. Softw. 20, 286-307.
247
248 The function is:
249
250 (1 - alpha)
251 phi'(alpha) = - gamma(beta1) * -------------------------------
252 sqrt((1 - alpha)**2 + beta2**2)
253
254 a
255 + gamma(beta2) * -------------------------
256 sqrt(alpha**2 + beta1**2)
257
258 where:
259 gamma(beta) = sqrt(1 + beta**2) - beta
260 """
261
262 temp = array([0.0], Float64)
263 g1 = sqrt(1.0 + beta1**2) - beta1
264 g2 = sqrt(1.0 + beta2**2) - beta2
265 a = -g1 * (1.0 - alpha[0]) / sqrt((1.0 - alpha[0])**2 + beta2**2)
266 b = g2 * alpha[0] / sqrt(alpha[0]**2 + beta1**2)
267 temp[0] = a + b
268 return temp
269
270
271 run()
272