for loop iteration-population conflict - python

I am new in python and I am trying to learn it by myself. I am currently working on a code, which gives me index error because somehow for loop does not populate my data. I am supposed to iterate a value and with it, I depend on the previous value to produce the new value. Normally this was easy with matlab, only with x(:,k) but python does not work the same way and I will really be grateful for any help that does not judge my level of knowledge in python. Here how it goes:
x = np.matrix([[1.2],[.2]]) # prior knowledge
A = np.matrix([[1, 1], [0, 1]])
B = np.matrix([[.5], [1]])
U = -9
t1 = range(1,100,1)
for k, val in enumerate(t1):
x[:,k] = A*x[:,k-1] + B*U
To my understanding, the error 'IndexError: index 1 is out of bounds for axis 1 with size 1' pops up because the for loop does not populate the data 'x' and therefore, there is no value for neither 'k-1' nor 'k'.
What I should do is to iterate and store 'x' values and pick the relevant previous value each time to obtain new value with given equation till the end of loop. As you can see, I have a column matrix and I should have a column matrix each time. I hope I could make myself clear.
Thank you

The first line is the initial value of x, the second, third, fourth and fifth lines are the values that are used in for loop to calculate iterations for x.
What I am trying to implement is code for kaman filter in general. In this system, the current value x(k) is calculated with previous value x(k-1) with given equation x(k) = Ax(k-1) + BU. Each x(k) value becomes x(k-1) in next iteration until loop is executed. Here, I am expecting to have (2,k) matrix after every loop because record of values are essential for other calculations. And to use the previous value in current value, I need to access to (k-1)th value.
The question was solved by juanpa.arrivillaga (https://stackoverflow.com/users/5014455/juanpa-arrivillaga) Thank you.

Related

How to loop through an xarray and calculating using an index in python

I have a data variable(sst) in an xarray(nino6), first I use enumerate to assign each value of data variable of the array an index, then I want to calculate with the values of data variable using the index. This code calculates with the indizes itself instead of the data variable values, but I just wanted you to show what I tried.
How can I loop through an index but actually calculating with the values?
for i, entry in enumerate(nino6['sst']):
a=((i-1)+i+(i+1))/3
ssta.append(a)
I apologise for my question is very likely to be really simple (I just started programming), but I searched unsuccesfully here and and on youtube.
If you are trying to get the average of every 3 adjacent numbers in sst, you do it like this:
lst = nino6['sst']
ssta = []
for i in range(1,len(lst) - 1):
a = (lst[i-1] + lst[i] + lst[i+1])/3
ssta.append(a)
Notice that in this implementation, the length of ssta will be smaller than the length of sst by 2 because the first and last numbers do not have flanking numbers. You can have other variations, where you just get the average of two numbers for the first and last numbers.

create loop using values from an array

I have an array D of variable length,
I want to create a loop that performs a sum based on the value of D corresponding to the number of times looped
i.e. the 5th run through the loop would use the 5th value in my array.
My code is:
period = 63 # can be edited to an input() command for variable periods.
Mrgn_dec = .10 # decimal value of 10%, can be manipulated to produce a 10% increase/decrease
rtn_annual = np.arange(0.00,0.15,0.05) # creates an array ??? not sure if helpful
sig_annual = np.arange(0.01,0.31,0.01) #use .31 as python doesnt include the upper range value.
#functions for variables of daily return and risk.
rtn_daily = (1/252)*rtn_annual
sig_daily = (1/(np.sqrt(252)))*sig_annual
D=np.random.normal(size=period) # unsure of range to use for standard distribution
for i in range(period):
r=(rtn_daily+sig_daily*D)
I'm trying to make it so my for loop is multiplied by the value for D of each step.
So D has a random value for every value of period, where period represents a day.
So for the 8th day I want the loop value for r to be multiplied by the 8th value in my array, is there a way to select the specific value or not?
Does the numpy.cumprod command offer any help, I'm not sure how it works but it has been suggested to help the problem.
You can select element in an iterative object (such as D in your code) simply by choosing its index. Such as:
for i in range(period):
print D[i]
But in your code, rtn_daily and sig_daily are not in the same shape, I assume that you want to add sig_daily multiply by D[i] in each position of rtn. so try this:
# -*- coding:utf-8 -*-
import numpy as np
period = 63 # can be edited to an input() command for variable periods.
Mrgn_dec = .10 # decimal value of 10%, can be manipulated to produce a 10% increase/decrease
rtn_annual = np.repeat(np.arange(0.00,0.15,0.05), 31) # creates an array ??? not sure if helpful
sig_annual = np.repeat(np.arange(0.01,0.31,0.01), 3) #use .31 as python doesnt include the upper range value.
#functions for variables of daily return and risk.
rtn_daily = (float(1)/252)*rtn_annual
sig_daily = (1/(np.sqrt(252)))*sig_annual
D=np.random.normal(size=period) # unsure of range to use for standard distribution
print D
for i in range(period):
r=(rtn_daily[i]+sig_daily[i]*D[i])
print r
Last of all, if you are using python2, the division method is for integer, so that means 1/252 will give you zero as result.
a = 1/252 >-- 0
to solve this you may try to make it float:
rtn_daily = (float(1)/252)*rtn_annual
Right now, D is just a scalar.
I'd suggest reading https://docs.scipy.org/doc/numpy-1.13.0/reference/generated/numpy.random.normal.html to learn about the parameters.
If you change it to:
D=np.random.normal(mean,stdev,period)
you will get a 1D array with period number of samples, where mean and stdev are your mean and standard deviation of the distribution. Then you change the loop to:
for i in range(period):
r=(rtn_daily+sig_daily*D[i])
EDIT: I don't know what I was thinking when I read the code the first time. It was a horribly bad read on my part.
Looking back at the code, a few things need to happen to make it work.
First:
rtn_annual = np.arange(0.00,0.15,0.05)
sig_annual = np.arange(0.01,0.31,0.01)
These two lines need to be fixed so that the dimensions of the resulting matricies are the same.
Then:
rtn_daily = (1/252)*rtn_annual
Needs to be changed so it doesn't zero everything out -- either change 1 to 1.0 or float(1)
Finally:
r=(rtn_daily+sig_daily*D)
needs to be changed to:
r=(rtn_daily+sig_daily*D[i])
I'm not really sure of the intent of the original code, but it appears as though the loop is unnecessary and you could just change the loop to:
r=(rtn_daily+sig_daily*D[day])
where day is the day you're trying to isolate.

Compute mean of last X elements of a list in Python2.7

Is there an elegant way or function to compute the mean of the last X elements of a list?
I have a list register that increases in size at each iterations :
register = np.append(register, value)
I want to create another list in which an i element corresponds to the mean of the X last elements in register
register_mean[i] = np.mean(register[i-X:i])
The tricky part is for the first X iterations, when there isn't X values yet in register. For these specific cases, I would like it to compute the mean on the firsts values of register, and only take the first value of register as first value of register_mean.
This could be done during the iterations or after, when register is complete.
I know there is lots of similar questions but haven't found one that answered this particular problem
Could it be something as simple as
if X < i:
register_mean[i] = np.mean(register[:i])
This just averages however many prior points there are until you have enough to average X points
Perhaps I misinterpreted your intent!
If I understand your question correctly, this should do the work:
X = 4 # Span of mean
register_mean = [np.mean(register[max(i-X, 0): max(i-X, 0) + 1]) for i in range(len(register))]
It will essentially create a moving average of the register elements between i - X and i; however, whenever i - X is negative, it will only take the values between 0 and i + 1.

Saving results from for loop and incrementing the index

I am new to Python and I'm writing a program to compute the resultants of distributed forces.
My method works like this:
force =[1,2,3,4,5]
distance =[2,3,4,5,6]
The idea is to break any section of a distributed force into 2 triangles whose area can be found using:
lowerarea = ((distance[i+1] - distance[i]) *force[i]) * 0.5
upperarea = ((distance[i+1] - distance[i]) *force[i+1]) * 0.5
This is my for loop to find the lower areas:
for i in range(0,len(force)):
lowerarea= (dist[i+1]-dist[i])*force[i]*0.5
print (f)
i = i+1
I obviously get the error that the index is out of bounds since d[6] doesn't exist how do i stop the loop once d[5] is evaluated?
Also how do i save the output of the loop f to a new variable?
Thanks!
The problem with the index going out of bounds is because you're doing an additional increment with i = i+1. Remove that line, because the loop is already doing that increment for you. By having it in there, you're pushing the value of i beyond len(force) - 1 (which as the other folks already pointed out is the highest index of these arrays).
As to f, you're not using or changing it at all during the loop, so why print it or try to store its value? The value isn't going to change anywhere in this code.
Why not create a new list?
results = []
for (...):
results.append(f)
Your out-of-range error is due to the fact that len(force) == 6 -- you want len(force) - 1.

Project Euler #82 (Python)

First of all this is the problem : https://projecteuler.net/problem=82 .
This is my code :
# https://projecteuler.net/problem=82
matrice = open('matrix3.txt','r').read().split('\n')
m = []
for el in matrice:
if el=='':
continue
tmp = el.split(',')
m.append(tmp)
matrix = [[0 for i in range(80)]for j in range(80)]
x,y = 0,0
while(True):
matrix[x][y]=int(m[x][y])
y+=1
if y==80:
y=0
x+=1
if x==80:
break
tmp = [0]*80
x,y = 0,78
while(True):
if x==0:
tmp[x]=min(matrix[x][y+1],matrix[x+1][y]+matrix[x+1][y+1])
if x==79:
tmp[x]=min(matrix[x][y+1],matrix[x-1][y]+matrix[x-1][y+1])
else:
tmp[x]=min(matrix[x][y+1],matrix[x-1][y]+matrix[x-1][y+1],matrix[x+1][y]+matrix[x+1][y+1])
x+=1
if x==80:
for e in range(80):
matrix[e][y]+=tmp[e]
tmp = [0]*80
x=0
y+=-1
if y<0:
break
minimo = 10**9
for e in range(80):
if matrix[e][0]<minimo:
minimo=matrix[e][0]
print(minimo)
The idea behind this code is the following:
I start from the 79th column(78th if you start counting from 0) and I calculate the best(the minimal) way to get from any given entry in that column to the column to the right.
When the column is over I replace it with the minimal results I found and I start doing the same with the column to the left.
Is anyone able to help me understand why I get the wrong answer?(I get 262716)
The same code works for the matrix in the example(It works if you change the indeces of course).
If I understand the question, your code, and your algorithm correctly, it looks like you aren't actually calculating the best way to get from one column to the next because you're only considering a couple of the possible ways to get to the next column. For example, consider the first iteration (when y=78). Then I think what you want is tmp[0] to hold the minimum sum for getting from matrix[0][78] to anywhere in the 79th column, but you only consider two possibilities: go right, or go down and then go right. What if the best way to get from matrix[0][78] to the next column is to go down 6 entries and then go right? Your code will never consider that possibility.
Your code probably works on the small example because it so happens that the minimum path only goes up or down a single time in each column. But I think that's a coincidence (also possibly a poorly chosen example).
One way to solve this problem is using the following approach. When the input is a NxN matrix, define a NxN array min_path. We're going to want to fill in min_path so that min_path[x][y] is the minimum path sum starting in any entry in the first column of the input matrix and ending at [x][y]. We fill in one column of min_path at a time, starting at the leftmost column. To compute min_path[i][j], we look at all entries in the (j-1)th column of min_path, and the cost of getting from each of those entries to (i, j). Here is some Python code showing this solution: https://gist.github.com/estark37/5216851. This is an O(N^4) solution but it can probably be made faster! (maybe by precomputing the results of the sum_to calls?)

Categories

Resources