# <span style='background:black'><span style='color:Cyan'> <span style='font-family:"Times New Roman"'> Copyright statement: 
#### <span style='font-family:"Times New Roman"'>The initial code was provided by Dr. Sandoval (Assitant professor of Electrical Engineering, New Mexico State University) as a starting point for project. https://web.nmsu.edu/~spsandov/ 
#### <span style='font-family:"Times New Roman"'>The algorithm in current form is developed by Sina Zamen. 

# <span style='background:black'><span style='color:Cyan'> <span style='font-family:"Times New Roman"'> Objective: 
## <span style='font-family:"Times New Roman"'>In this problem, convergence of Newton’s method for quadratic cost function, is considered. The initial weight vectors drawn from a Gaussian distribution with mean 0 and variance equal to 1. 

### <span style='font-family:"Times New Roman"'>Loading Required Modules:


```python
import math
import numpy as np
import sympy as sym
from PIL import Image
from numpy import array
from matplotlib import style
from numpy.linalg import inv
import matplotlib.pyplot as plt
style.use('ggplot')
```

### <span style='font-family:"Times New Roman"'>Defining Gaussian Dataset Generator Function:


```python
def circGuass(N,Me,VAR):
    dimension = len(Me)
    a = np.array(Me)
    p = np.random.randn(dimension,N)
    h = np.tile(a, (2, N//2))
    x = math.sqrt(Var) * p + h
    return x
```


```python
M1 = 0
Var = 1
N = 2
firstmean = [M1, M1]
Me = firstmean;
X = circGuass(N, Me, Var)
```

### <span style='font-family:"Times New Roman"'>Setting up countour map:


```python
HX ,HY  = 50,50 #number of x,y  points for countour
xmin,xmax = -15,15
ymin,ymax = -12,12
x1 = np.linspace(xmin,xmax,HX)
x2 = np.linspace(ymin,ymax,HY)
X1,X2 = np.meshgrid(x1,x2) # genertate mesh grid
w1=sym.Symbol('w1') # define symbols
w2=sym.Symbol('w2')
```


```python
bowl = 'bowl'
case2= ''
case = bowl #case select
if(case==bowl):
    j=(w1**2+w1*w2+3*w2**2)# define equation
elif(case==case2):
    #define other surfaces here
    pass
else:
    print('case not recognized')
```


```python
#compute gradient
j_grad1=sym.diff(j,w1)
j_grad2=sym.diff(j,w2)
#compute hessian
hess11=sym.diff(j_grad1,w1)
hess12=sym.diff(j_grad1,w2)
hess21=sym.diff(j_grad2,w1)
hess22=sym.diff(j_grad2,w2)

#generate contour map
ConMap=np.zeros((HX,HY))
for i in range(HX):
    for k in range(HY):
        ConMap[i,k]=j.subs({w1:x1[i],w2:x2[k]})


w=X[0,:] # starting point
wStar=[0,0] # ending point
ew=array([])
jw=array([100])
eta = 0.005 # learning rate
lim=200 # number of iterations
count= 0 
line=[]
h = jw.astype(int)
h = jw[-1:].astype(int)
while (h > 0.05):
    h = jw[-1:].astype(int)
    #compute gradient matrix and hessian matrix
    g= np.array([float(j_grad1.subs({w1:w[0],w2:w[1]})),float(j_grad2.subs({w1:w[0],w2:w[1]}))])
    H= np.array([[float(hess11.subs({w1:w[0],w2:w[1]})),float(hess12.subs({w1:w[0],w2:w[1]}))],                 [float(hess21.subs({w1:w[0],w2:w[1]})),float(hess22.subs({w1:w[0],w2:w[1]}))]])
    
    wnew1 =  w-eta*((inv(H)*np.asmatrix(g).T).T) 
    wnew = np.squeeze(np.asarray(wnew1))
    #loop check
    if( count>lim ):
        print('Count Break')
        break
    elif(np.isnan(g).any()):
        print('nan break')
        break
    else:
        count=count +1
        wprev=w.copy()
    
        line.append(w)
        w=wnew.copy()
        
        ew1 = (np.linalg.norm(w-wStar))
        jw1 = (j.subs({w1:w[0],w2:w[1]}))
        ew = np.append(ew, ew1)
        jw = np.append(jw, jw1)
line=np.array(line)  
```


```python
print("Number of Iterations:")
print(count)
```

    Number of Iterations:
    137



```python
plt.figure(figsize=(10,10))
plt.contour(X1,X2,ConMap)
plt.plot(line[:,1],line[:,0])
plt.scatter(line[:,1],line[:,0])
plt.plot(wStar[1],wStar[0],'go')
plt.show()
```


```python
plt.figure(figsize=(10,10))
plt.title('J(w) vs iterations')
plt.ylabel('J(w)')
plt.xlabel('iteration')
plt.plot(range(len(jw)),jw)
plt.show()
```


```python
plt.figure(figsize=(10,10))
plt.title('E(w) vs iterations')
plt.ylabel('E(w)')
plt.xlabel('iteration')
plt.plot(range(len(ew)),ew)
plt.show()
```

be519ec88f308eab3d60a2636226e21559fc6aa8
ipynb
Jupyter Notebook
Gradient Decent/Newtons Method Quadratic Cost Function.ipynb
Sinaconstantine/Machine-Learning-I-EE565
4d083b6ae91e9234a9d432bd9f5080bb87860c1a
CC0-1.0
Gradient Decent/Newtons Method Quadratic Cost Function.ipynb
Sinaconstantine/Machine-Learning-I-EE565
4d083b6ae91e9234a9d432bd9f5080bb87860c1a
CC0-1.0
Gradient Decent/Newtons Method Quadratic Cost Function.ipynb
Sinaconstantine/Machine-Learning-I-EE565
4d083b6ae91e9234a9d432bd9f5080bb87860c1a
CC0-1.0
Qwen/Qwen-72B
1. YES
2. YES