Array operations/ slicing in python from matlab - python

I have matlab array operations as the following :
[M,N]=size(I) ;
J = zeros(2*M,2*N) ;
J(1:2:end,1:2:end) = I ;
J(2:2:end-1,2:2:end-1) = 0.25*I(1:end-1,1:end-1) + 0.25*I(2:end,1:end-1) + 0.25*I(1:end-1,2:end) + 0.25*I(2:end,2:end) ;
J(2:2:end-1,1:2:end) = 0.5*I(1:end-1,:) + 0.5*I(2:end,:) ;
J(1:2:end,2:2:end-1) = 0.5*I(:,1:end-1) + 0.5*I(:,2:end) ;
I am trying to rewrite the same operations in python and I have come up with the following:
J=numpy.zeros((2*M,2*N))
J[::2,::2] = I ;
J[2:-1:2,2:-1:2] = 0.25*I[1::-1,1::-1] + 0.25*I[2::,1::-1] + 0.25*I[1::-1,2::] + 0.25*I[2::,2::]
J[2:-1:2,1::2] = 0.5*I[1::-1,] + 0.5*I[2::,]
J[::2,2:-1:2] = 0.5*I[:,1::-1] + 0.5*I[:,2::]
however the python code gives me different results.
can anyone tell me what is wrong?
Thanks,

Going through this piece by piece shows that you have some errors in your ranges. I think that you have misunderstood a few things about arrays in python.
Unlike matlab where the first element of an array is array[1], in python the first element of an array is array[0].
Array slicing syntax is array[start:stop:step], so to get every second element starting at the fifth element in the array to the end you would do array[4::2].
Just go through this piece by piece and you will find problems. For example, the first element on the right hand side of the second equation should be:
0.25*I[0:-1, 0:-1]
Note that you don't need the second colon here since your step is 1 and in cases where you want to change the step, the step goes last.

so here is the correct ported code:
J[::2,::2] = I ;
J[1:-1:2,2:-1:2] = 0.25*I[0:-1,0:-1] + 0.25*I[1::,0:-1] + 0.25*I[0:-1,1::] + 0.25*I[1::,1::]
J[1:-1:2,0::2] = 0.5*I[0:-1,] + 0.5*I[1::,]
J[0::2,1:-1:2] = 0.5*I[:,0:-1] + 0.5*I[:,1::]

Related

How to change the python string substring information

I have 1 bitsInfo string:
bitsInfo="0100001111110001"
and 1 array bitReplace which includes subarray:
bitReplace=[["1","5","00000"],["8","11","0000"]]
The first element of the subarray is startbit location and the second element is the endbit location.
The goal of the script is to replace the bitsInfo string (with the third element of subarray) base on startbit and endbit information.
The expected result should be
bitsFinal="0000001100000001"
I have tried this method:
for bits in bitReplace:
bitsFinal = bits[:int(bits[0])+bits[2]+ bits[int(bits[1]+1:]
This method doesn't really work. May I know what went wrong?
You are close but you are not using the original string anywhere. Try this:
bitsFinal = bitsInfo
for bits in bitReplace:
bitsFinal = bitsFinal[:int(bits[0])] + bits[2] + bitsFinal[int(bits[1])+1:]
the result is:
>>> bitsFinal
'0000001100000001'
for bits in bitReplace:
bitsFinal = bits[:int(bits[0])]+bits[2]+ bits[int(bits[1])+1:]
I think there are problems with parantheses.

pyomo accuracy; objective rule doesn´t return the expacted value

using pyomo and glpk solver I defind the follwing ojective rule:
def cost_rule(m):
return (sum(m.rd[i]*m.pRdImp*m.dt - m.vr[i]*m.pRdExp*m.dt for i in m.t) + m.cb + m.cPV + (150+10*m.kWp) )
m.cost = Objective(rule=cost_rule)
If I know compare the outputs after a minimum was found I get different results:
sum(m.rd[i]()*m.pRdImp()*m.dt() - m.vr[i]()*m.pRdExp()*m.dt() for i in t_t) + m.cPV() + m.cb() + (150+5*m.kWp())
Out[46]: 1136.468
m.cost()
Out[43]: 1173.178
(m.t and t_t are range sets representing the hours of a year)
This is an error of around 3 %, any ideas where is could come from? And which value would be the correct one if I would need to choose one.
Thanks in advance!
The expressions are different. The last term in the first one is (150+10*m.kWp) and the last term in the second one is (150+5*m.kWp())

How to remove the mean of some values in the 3rd dimension of a matrix?

I have been stuck trying to do this with numpy with no luck. I am trying to move from MATLAB to Python, however, the transition hasn't been so easy. Anyway, that doesn't matter.
I am trying to code the Python analog of this simple MATLAB line of code:
A(:,:,condtype==1 & Mat(:,9)==contra(ii)) = A(:,:, condtype ==1 & Mat(:,9)==contra(ii))-mean(A(:,:, condtype ==1 & Mat(:,9)==contra(ii)),3);
Right, so the above convoluted line of code does the following. Indexes a condition which is half of the 3rd dimension of A and removes the mean of those indexes which simultaneously changing the values in A to the new mean removed values.
How would one go about doing this in Python?
I actually figured it out. I was trying to use and when I should have been using np.isequal. Also, I needed to use keepdims=True for the mean. Here it is for anyone that wants to see:
def RmContrastMean(targettype,trialsMat,Contrastlvls,dX):
present = targettype==1
absent = targettype==0
for i in range(0,Contrastlvls.size):
CurrentContrast = trialsMat[:,8]==Contrastlvls[i]
preIdx = np.equal(present, CurrentContrast)
absIdx = np.equal(absent, CurrentContrast)
#mean
dX[:,:,preIdx] = dX[:,:,preIdx]-np.mean(dX[:,:,preIdx],axis=2,keepdims=True)
dX[:,:,absIdx] = dX[:,:,absIdx]-np.mean(dX[:,:,absIdx],axis=2,keepdims=True)
#std
dX[:,:,preIdx] = dX[:,:,preIdx]/np.std(dX[:,:,preIdx],axis=2,keepdims=True)
dX[:,:,absIdx] = dX[:,:,absIdx]/np.std(dX[:,:,absIdx],axis=2,keepdims=True)
return dX

How to automatically create list with 550 elements each, without the need to rename each one manually?

I would heavily need your help to simplify a code that allows me to have a data analysis on salesforce leads.
I have the following dataframes, which as you can see are split due to python limit on managing more than 550 objects in a single list.
Iterlist = list()
for x in range(0, int(len(List)/550)+1):
m = List[550*x: 550*x+550]
Iterlist.append(m)
Iterlist0= pd.DataFrame(Iterlist[0])
Iterlist1= pd.DataFrame(Iterlist[1])
Iterlist2= pd.DataFrame(Iterlist[2])
...and so on until the initial longer list is split
...
converted in the following lists for formatting reasons:
A= Iterlist0["Id"].tolist()
mylistA = "".join(str(x)+ "','" for x in A)
mylistA = mylistA[:-2]
mylistA0 = "('" + mylistA + ")"
B = Iterlist1["Id"].tolist()
mylistB = "".join(str(x)+ "','" for x in B)
mylistB = mylistB[:-2]
mylistB1 = "('" + mylistB + ")"
C = Iterlist2["Id"].tolist()
mylistC = "".join(str(x)+ "','" for x in C)
mylistC = mylistC[:-2]
mylistC2 = "('" + mylistC + ")"
and so on...
...
I want to create a loop that allows me to query from salesforce each of the lists using the following code template for example:
queryA='SELECT '+cols[1]+', '+cols[2]+', '+cols[3]+', '+cols[4]+', '+cols[5]+', '+cols[6]+', '+cols[7]+', '+cols[8]+' FROM LeadHistory WHERE LeadId IN '+mylistA0
and then finally:
sf = Salesforce(username='xxx', password='xxx', security_token='xxx')
leadhistory = sf.query_all(queryA)
I don´t want to write over and over numerous dataframes with specific names, lists and queries in order to get to the result. I would like to have a line for each of the codes written above, and let python automatically update the naming according to the number of 550 elements list.
I am new to this programming language and any tip would help me a lot. I think is possible to simplify it a lot but no idea how can be done.
Thanks in advance!

difficulty in matlab to python code conversion

I am converting matlab code to python code
function Xn = ReSampleCurve(X,N)
[n,T] = size(X);
del(1) = 0;
for r = 2:T
del(r) = norm(X(:,r) - X(:,r-1));
end
cumdel = cumsum(del)/sum(del);
newdel = [0:N-1]/(N-1);
for j=1:n
Xn(j,:) = interp1(cumdel,X(j,1:T),newdel,'linear');
end
I want to convert this into python code
The input values are :
X = [[-9.035250067710876, 7.453250169754028, 33.34074878692627], [-6.63700008392334, 5.132999956607819, 31.66075038909912],[-5.1272499561309814, 8.251499891281128, 30.925999641418457], [-5.1272499561309814, 8.251499891281128, 30.925999641418457]]
N = 200
can anyone explains me what these lines do?
del(1) = 0;
for r = 2:T
del(r) = norm(X(:,r) - X(:,r-1));
For what it is worth, here is the vectorized way to get del(2:end) in Matlab, perhaps this makes more sense to you:
sqrt(sum(diff(M,1,2).^2))
del is an array in the MATLAB code. So del(1) = 0 is equivalent to del_list = [0] (MATLAB arrays a 1-indexed, del is a reserved word in python).
In the for loop, this is equivalent to:
for r in range(1,T):
del_list.append(norm(X[:,r] - X[:,r-1]))
The above won't work in pure python (array subtraction won't work). You'd have to add in numpy or numeric) - but hopefully you get the idea.

Categories