1use rustad::{
8 AD,
9 ad_from_value,
10 ad_from_vector,
11 NumVec,
12 start_recording,
13 stop_recording,
14};
15fn example_hessian () {
19 type V = f32;
21 let nx = 3;
22 let trace = false;
23 let x : Vec<V> = vec![ 2.0 as V; nx ];
26 let ax = start_recording(x.clone());
29 let mut asum : AD<V> = ad_from_value( 0.0 as V );
32 for j in 0 .. nx {
33 let cubed = &( &ax[j] * &ax[j] ) * &ax[j];
34 asum += &cubed;
35 }
36 let ay = vec![ asum ];
40 let f = stop_recording(ay);
41 let ax = start_recording(x);
44 let mut av : Vec< AD<V> > = Vec::new();
45 f.forward_zero_ad(&mut av, ax, trace);
46 let dy : Vec<V> = vec![ 1.0 as V ];
50 let ady = ad_from_vector(dy);
51 let adx = f.reverse_one_ad(&av, ady, trace);
52 let g = stop_recording(adx);
53 let mut x : Vec<V> = Vec::new();
57 for j in 0 .. nx {
58 x.push( (j+2) as V );
59 }
60 let mut v : Vec<V> = Vec::new();
63 let y = g.forward_zero_value(&mut v, x, trace);
64 for j in 0 .. nx {
65 let check = 3 * (j+2) * (j+2);
66 assert_eq!( y[j], check as V );
67 }
68 for j in 0 .. nx {
72 let mut dx : Vec<V> = vec![ 0.0 as V; nx ];
73 dx[j] = 1.0 as V;
74 let dy = g.forward_one_value(&v, dx, trace);
75 for i in 0 .. nx {
76 if i == j {
77 let check = 6 * (j+2);
78 assert_eq!( dy[i], check as V );
79 } else {
80 assert_eq!( dy[i], 0.0 as V );
81 }
82 }
83 }
84}
85fn example_numvec_hessian () {
89 type F = f64;
91 type V = NumVec<F>;
92 let nx = 3;
93 let trace = false;
94 let mut x : Vec<V> = Vec::new();
97 for _j in 0 .. nx {
98 x.push( NumVec::new( vec![ 2.0 as F ] ) );
99 }
100 let ax = start_recording(x.clone());
103 let mut asum : AD<V> = ad_from_value( NumVec::from( 0.0 as F ) );
106 for j in 0 .. nx {
107 let cubed = &( &ax[j] * &ax[j] ) * &ax[j];
108 asum += &cubed;
109 }
110 let ay = vec![ asum ];
114 let f = stop_recording(ay);
115 let ax = start_recording(x);
118 let mut av : Vec< AD<V> > = Vec::new();
119 f.forward_zero_ad(&mut av, ax, trace);
120 let dy : Vec<V> = vec![ NumVec::from( 1.0 as F ) ];
124 let ady = ad_from_vector(dy);
125 let adx = f.reverse_one_ad(&av, ady, trace);
126 let g = stop_recording(adx);
127 let mut x : Vec<V> = Vec::new();
131 for j in 0 .. nx {
132 x.push( NumVec::new( vec![ (j+1) as F, (j+2) as F ] ) );
133 }
134 let mut v : Vec<V> = Vec::new();
137 let y = g.forward_zero_value(&mut v, x, trace);
138 for j in 0 .. nx {
139 let check = 3 * (j+1) * (j+1);
141 assert_eq!( y[j].get(0), check as F );
142 let check = 3 * (j+2) * (j+2);
144 assert_eq!( y[j].get(1), check as F );
145 }
146 for j in 0 .. nx {
150 let mut dx : Vec<V> = vec![ NumVec::from( 0.0 as F ); nx ];
151 dx[j] = NumVec::from( 1.0 as F );
152 let dy = g.forward_one_value(&v, dx, trace);
153 for i in 0 .. nx {
154 if i == j {
155 let check = 6 * (j+1);
157 assert_eq!( dy[i].get(0), check as F );
158 let check = 6 * (j+2);
160 assert_eq!( dy[i].get(1), check as F );
161 } else {
162 for k in 0 .. dy[i].len() {
163 assert_eq!( dy[i].get(k) , 0.0 as F );
164 }
165 }
166 }
167 }
168}
169fn main() {
170 example_hessian();
171 example_numvec_hessian();
172}