I was wondering how to go about reordering numpy arrays on different axes and with two shared dimensions. For instance, say I have the following (truncated) array of shape (3, 57, 2):
A = array([[[0.93191024, 0.15612787],
[0.71642773, 0.56644261],
[0.56412285, 0.53022111],
[0.08851486, 0.16253565],
[0.34093212, 0.41074817],
[0.02038229, 0.03693136],
[0.09371394, 0.06565686],
[0.93267282, 0.21915236],
[0.96060752, 0.07309468],
[0.82970486, 0.59032961],
[0.3997659 , 0.51113411],
[0.9933917 , 0.1476475 ],
[0.45059107, 0.98992075],
[0.64420259, 0.99047411],
[0.11300111, 0.15220392],
[0.28461117, 0.63130115],
[0.31121419, 0.62935332],
[0.05057692, 0.22276605],
[0.44223485, 0.47280298],
[0.45543663, 0.53295429],
[0.41775544, 0.90341879],
[0.80630092, 0.42294245],
[0.82215799, 0.78450402],
[0.53719004, 0.56694119],
[0.47927382, 0.55033868],
[0.51007433, 0.27610559],
[0.33946435, 0.97437761],
[0.97263574, 0.07449039],
[0.840479 , 0.84473952],
[0.65787646, 0.91151828],
[0.93803356, 0.35804058],
[0.93322294, 0.38717009],
[0.4193876 , 0.54307245],
[0.9016539 , 0.31755714],
[0.66398876, 0.40193374],
[0.65885493, 0.83359592],
[0.32875318, 0.23673417],
[0.87984555, 0.39703699],
[0.69733635, 0.59550783],
[0.81226642, 0.05097729],
[0.12092097, 0.45202225],
[0.17937865, 0.50205434],
[0.32294824, 0.7195445 ],
[0.78753686, 0.69291673],
[0.24804844, 0.30187789],
[0.0446775 , 0.81477633],
[0.505237 , 0.29917803],
[0.67580571, 0.95910518],
[0.08254148, 0.74803897],
[0.43566526, 0.31926868],
[0.4359975 , 0.2017858 ],
[0.19281317, 0.31834615],
[0.89746816, 0.05457466],
[0.3012639 , 0.24771521],
[0.60127988, 0.2070745 ],
[0.01068053, 0.15385391],
[0.36193366, 0.80346892]],
[[0.84691843, 0.64659873],
[0.4138493 , 0.65155583],
[0.1952568 , 0.79107071],
[0.44328237, 0.96547454],
[0.25811086, 0.63944066],
[0.85353904, 0.24630087],
[0.02200961, 0.43702606],
[0.51187364, 0.21604095],
[0.80455184, 0.72895394],
[0.56534909, 0.9832036 ],
[0.56615037, 0.41387091],
[0.15117167, 0.96842998],
[0.45100418, 0.33455142],
[0.76995385, 0.80203815],
[0.09164816, 0.08733553],
[0.0885783 , 0.03341749],
[0.56167238, 0.18389973],
[0.66844602, 0.84802942],
[0.52667165, 0.82921114],
[0.3668573 , 0.79127918],
[0.83358175, 0.2357053 ],
[0.99023907, 0.72416636],
[0.04969955, 0.16445317],
[0.83618043, 0.61106043],
[0.44079159, 0.53960843],
[0.28535309, 0.57542243],
[0.02355444, 0.96444916],
[0.99996202, 0.22699034],
[0.35725371, 0.3284021 ],
[0.24784074, 0.10957504],
[0.68893807, 0.33428212],
[0.19549847, 0.53242997],
[0.37411674, 0.10671197],
[0.38613786, 0.71247659],
[0.58098534, 0.46313774],
[0.94364596, 0.74239641],
[0.94446665, 0.80260609],
[0.15405246, 0.20687026],
[0.06607917, 0.39675446],
[0.49393799, 0.98976068],
[0.90401917, 0.21254029],
[0.39854018, 0.51468104],
[0.57275152, 0.23703318],
[0.28854573, 0.61574602],
[0.33767913, 0.71972114],
[0.29835304, 0.21042103],
[0.53764989, 0.10600488],
[0.93471516, 0.22275683],
[0.46161675, 0.71566021],
[0.60435755, 0.29129393],
[0.93588236, 0.45631744],
[0.68130624, 0.14505727],
[0.26229578, 0.16338432],
[0.61311318, 0.07904725],
[0.42231007, 0.40815435],
[0.18240378, 0.18156717],
[0.32826971, 0.51764318]],
[[0.61310538, 0.70781868],
[0.81069552, 0.40163557],
[0.41225382, 0.55698844],
[0.79904472, 0.57460263],
[0.15534107, 0.14216233],
[0.07721588, 0.00293088],
[0.75088213, 0.15521204],
[0.0505958 , 0.70318609],
[0.40682637, 0.77522382],
[0.65678125, 0.42817843],
[0.98454818, 0.0959132 ],
[0.04875253, 0.33109192],
[0.96330185, 0.01330943],
[0.06014761, 0.90105887],
[0.88935171, 0.82924489],
[0.68668051, 0.92581709],
[0.64966411, 0.33036089],
[0.92391759, 0.13665613],
[0.78596527, 0.01177382],
[0.36857492, 0.97854483],
[0.11493051, 0.63332842],
[0.89560528, 0.24904867],
[0.19925101, 0.78383848],
[0.16796212, 0.86980891],
[0.64345971, 0.87019182],
[0.98074058, 0.66858333],
[0.89239524, 0.68869392],
[0.05101222, 0.06246318],
[0.19412597, 0.58740619],
[0.47544267, 0.66208743],
[0.30888323, 0.03953938],
[0.39305549, 0.24437666],
[0.34944342, 0.94852464],
[0.93839378, 0.30905846],
[0.28667766, 0.18239694],
[0.93015124, 0.23186617],
[0.41991688, 0.6963337 ],
[0.73953573, 0.99268293],
[0.13625265, 0.40126139],
[0.5658131 , 0.81199939],
[0.34594279, 0.90360269],
[0.95083541, 0.97844242],
[0.13066022, 0.16431073],
[0.31765483, 0.41965885],
[0.99760275, 0.77221808],
[0.64802972, 0.71946862],
[0.35160349, 0.64195416],
[0.03926753, 0.27586446],
[0.98373212, 0.55210807],
[0.76304081, 0.62046984],
[0.75019444, 0.4965763 ],
[0.99821063, 0.92457013],
[0.8526248 , 0.0722389 ],
[0.01161104, 0.36656463],
[0.54781289, 0.32044447],
[0.68337198, 0.20499322],
[0.41070141, 0.72194802]]])
And I want to rearrange the elements at dimensions 0 and 1 with an ndarray representing indices of shape (3, 57), i.e. for each row I want to rearrange the 57 entries according to each index list of 57:
B = array([[12, 1, 9, 10, 5, 2, 7, 8, 6, 16, 4, 0, 11, 14, 13, 22,
21, 29, 3, 15, 28, 27, 18, 23, 34, 20, 33, 31, 25, 35, 26, 24,
32, 30, 17, 19, 40, 36, 39, 41, 47, 43, 37, 49, 44, 46, 45, 38,
42, 48, 50, 53, 52, 54, 51, 55, 56],
[46, 42, 55, 52, 31, 24, 43, 48, 44, 49, 35, 51, 33, 53, 16, 41,
10, 4, 7, 13, 22, 8, 40, 15, 5, 12, 1, 9, 25, 3, 30, 26,
6, 0, 34, 14, 32, 2, 28, 27, 39, 11, 17, 21, 20, 19, 23, 18,
45, 36, 50, 38, 37, 29, 47, 54, 56],
[ 4, 1, 14, 12, 6, 8, 0, 11, 13, 7, 2, 3, 9, 5, 16, 10,
27, 28, 20, 22, 32, 25, 15, 37, 17, 34, 24, 18, 19, 43, 39, 26,
23, 29, 30, 47, 45, 21, 31, 33, 35, 38, 44, 46, 40, 50, 36, 48,
49, 51, 41, 42, 52, 53, 54, 55, 56]])
How would I go about transforming array A by indices array B?
If the first dimension is 3 you can use:
np.array([A[i, B[i]] for i in range(len(A))])
#5.13 µs ± 14.7 ns per loop (mean ± std. dev. of 7 runs, 100,000 loops each)
Otherwise, for longer arrays, you should look for a more performing solution.
Related
I'm struggling with tables for matplotlib (blume). The table is for an automation project that will produce 22 different maps. The code below produce a table with 49 rows. Some figures will only have 6 rows. When the number of rows exceeds 25 I would like to use two columns.
import pandas as pd
import matplotlib.pyplot as plt
from blume.table import table
# Dataframe
df=pd.DataFrame({'nr': [ 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, 27, 28, 29, 30, 31, 32, 33, 34,
35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49],
'KnNamn': ['Härryda', 'Partille', 'Öckerö', 'Stenungsund', 'Tjörn', 'Orust',
'Sotenäs', 'Munkedal', 'Tanum', 'Dals-Ed', 'Färgelanda', 'Ale',
'Lerum', 'Vårgårda', 'Bollebygd', 'Grästorp', 'Essunga',
'Karlsborg', 'Gullspång', 'Tranemo', 'Bengtsfors', 'Mellerud',
'Lilla Edet', 'Mark', 'Svenljunga', 'Herrljunga', 'Vara', 'Götene',
'Tibro', 'Töreboda', 'Göteborg', 'Mölndal', 'Kungälv', 'Lysekil',
'Uddevalla', 'Strömstad', 'Vänersborg', 'Trollhättan', 'Alingsås',
'Borås', 'Ulricehamn', 'Åmål', 'Mariestad', 'Lidköping', 'Skara',
'Skövde', 'Hjo', 'Tidaholm', 'Falköping'],
'rel': [0.03650425, 0.05022105, 0.03009109, 0.03966735, 0.02793296,
0.03690838, 0.04757161, 0.05607283, 0.0546372 , 0.05452821,
0.06640368, 0.04252673, 0.03677577, 0.05385784, 0.0407173 ,
0.04024881, 0.05613226, 0.04476127, 0.08543165, 0.04070175,
0.09281077, 0.08711656, 0.06111578, 0.04564958, 0.05058988,
0.04618078, 0.04640402, 0.04826498, 0.08514253, 0.07799246,
0.07829886, 0.04249149, 0.03909206, 0.06835601, 0.08027622,
0.07087295, 0.09013876, 0.1040369 , 0.05004451, 0.06584845,
0.04338739, 0.10570863, 0.0553109 , 0.05024871, 0.06531729,
0.05565605, 0.05041816, 0.04885198, 0.07954831]})
# Table
fig,ax = plt.subplots(1, figsize=(10, 7))
val =[]
ax.axis('off')
for i, j, k in zip(df.nr, df.KnNamn, df.rel):
k = k*100
k = round(k,2)
k= (str(k) + ' %')
temp=str(i)+'. ' +str(j)+': ' + str(k)
val.append(temp)
val=[[el] for el in val]
#val=val[0] + val[1]
tab=table(ax,cellText=val,
#rowLabels=row_lab,
colLabels=['Relativ arbetslöshet'], loc='left', colWidths=[0.3], cellLoc='left')
plt.show()
As I understands it, if I want a table with two columns, my val object should be structured in a different way. In the case above, val is a nested list with 49 lists inside. I need to merge lists, I figure. I tried this pairwise for loop but that didn't work with range?
I'm sure there is a simple solution to this problem I have. Help would be much appreciated.
for i, j in zip(range(len(val)), range(len(val))[1:] + range(len(val))[:1]):
print(i, j)
I don't know if it is what you need but you could use zip() or better itertools.zip_longest() with val[:25], val[25:]
two_columns = []
for col1, col2 in itertools.zip_longest(values[:25], values[25:], fillvalue=''):
#print(f'{col1:25} | {col2}')
two_columns.append([col1, col2])
Full working example
import pandas as pd
import matplotlib.pyplot as plt
from blume.table import table
import itertools
df = pd.DataFrame({
'nr': [
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, 27, 28, 29, 30, 31, 32, 33, 34,
35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49
],
'KnNamn': [
'Härryda', 'Partille', 'Öckerö', 'Stenungsund', 'Tjörn', 'Orust',
'Sotenäs', 'Munkedal', 'Tanum', 'Dals-Ed', 'Färgelanda', 'Ale',
'Lerum', 'Vårgårda', 'Bollebygd', 'Grästorp', 'Essunga',
'Karlsborg', 'Gullspång', 'Tranemo', 'Bengtsfors', 'Mellerud',
'Lilla Edet', 'Mark', 'Svenljunga', 'Herrljunga', 'Vara', 'Götene',
'Tibro', 'Töreboda', 'Göteborg', 'Mölndal', 'Kungälv', 'Lysekil',
'Uddevalla', 'Strömstad', 'Vänersborg', 'Trollhättan', 'Alingsås',
'Borås', 'Ulricehamn', 'Åmål', 'Mariestad', 'Lidköping', 'Skara',
'Skövde', 'Hjo', 'Tidaholm', 'Falköping'
],
'rel': [
0.03650425, 0.05022105, 0.03009109, 0.03966735, 0.02793296,
0.03690838, 0.04757161, 0.05607283, 0.0546372 , 0.05452821,
0.06640368, 0.04252673, 0.03677577, 0.05385784, 0.0407173 ,
0.04024881, 0.05613226, 0.04476127, 0.08543165, 0.04070175,
0.09281077, 0.08711656, 0.06111578, 0.04564958, 0.05058988,
0.04618078, 0.04640402, 0.04826498, 0.08514253, 0.07799246,
0.07829886, 0.04249149, 0.03909206, 0.06835601, 0.08027622,
0.07087295, 0.09013876, 0.1040369 , 0.05004451, 0.06584845,
0.04338739, 0.10570863, 0.0553109 , 0.05024871, 0.06531729,
0.05565605, 0.05041816, 0.04885198, 0.07954831
]
})
# df = df[:25] # test for 25 rows
# ---
fig, ax = plt.subplots(1, figsize=(10, 7))
ax.axis('off')
# --- values ---
#values = []
#for number, name, rel in zip(df.nr, df.KnNamn, df.rel):
# text = f'{number}. {name}: {rel*100:.2} %'
# values.append(text)
values = df.apply(lambda row: f'{row["nr"]}. {row["KnNamn"]}: {row["rel"]*100:.2} %', axis=1).values
# --- columns ---
if len(values) > 25:
two_columns = []
for col1, col2 in itertools.zip_longest(values[:25], values[25:], fillvalue=''):
#print(f'{col1:25} | {col2}')
two_columns.append([col1, col2])
tab = table(ax, cellText=two_columns,
#rowLabels=row_lab,
colLabels=['Col1', 'Col2'], colWidths=[0.3, 0.3], loc=-100, cellLoc='left')
else:
one_column = [[item] for item in values]
tab = table(ax, cellText=one_column,
#rowLabels=row_lab,
colLabels=['Col1'], colWidths=[0.3], loc=-100, cellLoc='left')
# --- plot ---
plt.show()
Result:
EDIT:
More universal version which can create many columns.
Example automatically create 3 columns for ROWS = 20.
import pandas as pd
import matplotlib.pyplot as plt
from blume.table import table
import itertools
df = pd.DataFrame({
'nr': [
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, 27, 28, 29, 30, 31, 32, 33, 34,
35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49
],
'KnNamn': [
'Härryda', 'Partille', 'Öckerö', 'Stenungsund', 'Tjörn', 'Orust',
'Sotenäs', 'Munkedal', 'Tanum', 'Dals-Ed', 'Färgelanda', 'Ale',
'Lerum', 'Vårgårda', 'Bollebygd', 'Grästorp', 'Essunga',
'Karlsborg', 'Gullspång', 'Tranemo', 'Bengtsfors', 'Mellerud',
'Lilla Edet', 'Mark', 'Svenljunga', 'Herrljunga', 'Vara', 'Götene',
'Tibro', 'Töreboda', 'Göteborg', 'Mölndal', 'Kungälv', 'Lysekil',
'Uddevalla', 'Strömstad', 'Vänersborg', 'Trollhättan', 'Alingsås',
'Borås', 'Ulricehamn', 'Åmål', 'Mariestad', 'Lidköping', 'Skara',
'Skövde', 'Hjo', 'Tidaholm', 'Falköping'
],
'rel': [
0.03650425, 0.05022105, 0.03009109, 0.03966735, 0.02793296,
0.03690838, 0.04757161, 0.05607283, 0.0546372 , 0.05452821,
0.06640368, 0.04252673, 0.03677577, 0.05385784, 0.0407173 ,
0.04024881, 0.05613226, 0.04476127, 0.08543165, 0.04070175,
0.09281077, 0.08711656, 0.06111578, 0.04564958, 0.05058988,
0.04618078, 0.04640402, 0.04826498, 0.08514253, 0.07799246,
0.07829886, 0.04249149, 0.03909206, 0.06835601, 0.08027622,
0.07087295, 0.09013876, 0.1040369 , 0.05004451, 0.06584845,
0.04338739, 0.10570863, 0.0553109 , 0.05024871, 0.06531729,
0.05565605, 0.05041816, 0.04885198, 0.07954831
]
})
#df = df[:25] # test for 25 rows
# ---
fig, ax = plt.subplots(1, figsize=(10, 7))
ax.axis('off')
# --- values ---
def convert(row):
return f'{row["nr"]}. {row["KnNamn"]}: {row["rel"]*100:.2} %'
values = df.apply(convert, axis=1).values
# --- columns ---
ROWS = 20
#ROWS = 25
columns = []
for idx in range(0, len(values), ROWS):
columns.append(values[idx:idx+ROWS])
columns_widths = [0.3] * len(columns)
columns_labels = [f'Col{i}' for i in range(1, len(columns)+1)]
rows = list(itertools.zip_longest(*columns, fillvalue=''))
# --- plot ---
tab = table(ax,
cellText=rows,
#rowLabels=row_lab,
colLabels=columns_labels,
colWidths=columns_widths,
loc=-100,
cellLoc='left')
plt.show()
Result:
I am new to python, and I wondered if anyone could help me find the average in the following marks list of students?. Please advise as to what I am doing wrong here.
student_marks = [['Name', ['A','B','C','D','E']],
['Ankit', [41, 34, 45, 55, 63]],
['Aravind',[42, 23, 34, 44, 53]],
['Lakshay',[32, 23, 13, 54, 67]],
['Gyan', [23, 82, 23, 63, 34]],
['Pranav', [21, 23, 25, 56, 56]]
]
for student in student_marks[1:]:
marks_in_C = student[1][2]
print(marks_in_C, end=" ")
total = sum(marks_in_C)
TypeError: 'int' object is not iterable
You can find the average of C in this two ways:
student_marks = [['Name', ['A','B','C','D','E']],
['Ankit', [41, 34, 45, 55, 63]],
['Aravind',[42, 23, 34, 44, 53]],
['Lakshay',[32, 23, 13, 54, 67]],
['Gyan', [23, 82, 23, 63, 34]],
['Pranav', [21, 23, 25, 56, 56]]
]
total_C = 0
for [name, [A, B, C, D, E]] in student_marks[1:]:
total_C += C
avg_of_C = total_C / len(student_marks[1:])
print(avg_of_C)
OR
student_marks = [['Name', ['A','B','C','D','E']],
['Ankit', [41, 34, 45, 55, 63]],
['Aravind',[42, 23, 34, 44, 53]],
['Lakshay',[32, 23, 13, 54, 67]],
['Gyan', [23, 82, 23, 63, 34]],
['Pranav', [21, 23, 25, 56, 56]]
]
marks_in_C = list()
for [name, [A, B, C, D, E]] in student_marks[1:]:
marks_in_C.append(C)
avg_of_C = sum(marks_in_C) / len(marks_in_C)
print(avg_of_C)
Welcome to Python world! The error occurred because you are using int type data to be iterated. sum() method expect iterable data but marks_in_C has only one integer which cannot be iterated
I think you are trying to use marks_in_C as a list. why don't you use your loop looks like this?
...
marks_in_C = list()
for student in student_marks[1:]:
marks_in_C.append(student[1][2])
print(marks_in_C, end=" ")
total = sum(marks_in_C)
hope it to help you.
I have two numpy arrays of different dimensions:
x.shape = (1,1,M) and Y.shape = (N,N).
How do I perform Z = x - Y efficiently in python, such that Z.shape = (N,N,M), where - is an elementwise subtraction operation.
For example, M=10
x = array([[[1, 2, 3, 4, 5 , 6, 7, 8, 9, 10]]])
and N=8
Y = array([[11, 12, 13, 14, 15, 16, 17, 18],
[21, 22, 23, 24, 25, 26, 27, 28],
[31, 32, 33, 34, 35, 36, 37, 38],
[41, 42, 43, 44, 45, 46, 47, 48],
[51, 52, 53, 54, 55, 56, 57, 58],
[61, 62, 63, 64, 65, 66, 67, 68],
[71, 72, 73, 74, 75, 76, 77, 78],
[81, 82, 83, 84, 85, 86, 87, 88]])
Now the idea is to get a Z such that
Z[:,:,0] = array([[1-11, 1-12, 1-13, 1-14, 1-15, 1-16, 1-17, 1-18],
[1-21, 1-22, 1-23, 1-24, 1-25, 1-26, 1-27, 1-28],
[1-31, 1-32, 1-33, 1-34, 1-35, 1-36, 1-37, 1-38],
[1-41, 1-42, 1-43, 1-44, 1-45, 1-46, 1-47, 1-48],
[1-51, 1-52, 1-53, 1-54, 1-55, 1-56, 1-57, 1-58],
[1-61, 1-62, 1-63, 1-64, 1-65, 1-66, 1-67, 1-68],
[1-71, 1-72, 1-73, 1-74, 1-75, 1-76, 1-77, 1-78],
[1-81, 1-82, 1-83, 1-84, 1-85, 1-86, 1-87, 1-88]])
and
Z[:,:,9] = array([[10-11, 10-12, 10-13, 10-14, 10-15, 10-16, 10-17, 10-18],
[10-21, 10-22, 10-23, 10-24, 10-25, 10-26, 10-27, 10-28],
[10-31, 10-32, 10-33, 10-34, 10-35, 10-36, 10-37, 10-38],
[10-41, 10-42, 10-43, 10-44, 10-45, 10-46, 10-47, 10-48],
[10-51, 10-52, 10-53, 10-54, 10-55, 10-56, 10-57, 10-58],
[10-61, 10-62, 10-63, 10-64, 10-65, 10-66, 10-67, 10-68],
[10-71, 10-72, 10-73, 10-74, 10-75, 10-76, 10-77, 10-78],
[10-81, 10-82, 10-83, 10-84, 10-85, 10-86, 10-87, 10-88]])
and so on.
It is easy to do in MATLAB using just - operation. But Python does not support it.
The answer is: use different shape of y:
>>> y = y.reshape((8, 8, 1))
>>> (x-y).shape
(8, 8, 10)
This is a vizualization for better understanding with smaller dimensions:
You can compute your result without explicit creation of a reshaped array,
but using Numpy broadcasting.
The key to success is to add a new dimension to Y, using np.newaxis:
Z = x - Y[:, :, np.newaxis]
So I have an array of 5 integers v and another of 10 integers v.
I have a 5 by 10 matrix P that I would want to fill so that (P)ij = v[i] + u[j]
I tried:
P = np.empty((len(asset_grid),len(asset_grid)))
for i in range(asset_grid):
for j in range(asset_grid):
P[i,j] = asset_grid[i] + asset_grid[j]
but it gives me an error
TypeError: only integer arrays with one element can be converted to an index
How should I be able to do this in Python. I apologize if my approach is too naive, I am used to Matlab and now slowly learning Python. Any help is appreciated.
Broadcasting is what you want to do. Although for small arrays such as yours, it doesn't make a difference, it makes a significant difference with larger arrays:
>>> arr1 = np.arange(5)
>>> arr2 = np.arange(10,20)
>>> arr1[:,None] + arr2
array([[10, 11, 12, 13, 14, 15, 16, 17, 18, 19],
[11, 12, 13, 14, 15, 16, 17, 18, 19, 20],
[12, 13, 14, 15, 16, 17, 18, 19, 20, 21],
[13, 14, 15, 16, 17, 18, 19, 20, 21, 22],
[14, 15, 16, 17, 18, 19, 20, 21, 22, 23]])
Generally with numpy you want to avoid iteration over rows and columns and use vectorized/broadcasted operations. This is where speed improvements actually come from.
So, elaborating based on your comment:
Say P_ij is ith element of x raised to the 4th power minus jth element of y raised to 2nd power
In general, Python supports most arithmetical operations you would want in a vectorized way, using the usual Python operators:
>>> arr1[:, None]**4 - arr2**2
array([[-100, -121, -144, -169, -196, -225, -256, -289, -324, -361],
[ -99, -120, -143, -168, -195, -224, -255, -288, -323, -360],
[ -84, -105, -128, -153, -180, -209, -240, -273, -308, -345],
[ -19, -40, -63, -88, -115, -144, -175, -208, -243, -280],
[ 156, 135, 112, 87, 60, 31, 0, -33, -68, -105]])
I want to get rid of the first "pts", and 2 as the key of loc and pts and imsize, loc, pts, imsize are the key of their values.
This is my list:
test = [{'pts': u"""{"2": {"loc": [11, 12, 13, 14, 15, 16, 17, 18, 19, 20,
21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32], "pts": [[
238.12358231315642, 253.66068427891196], [458.64277680287756,
241.96368624623565], [697.01528407931528, 227.18853083653903],
[958.16615594570135, 201.82451404989325], [1246.281686434784,
203.42515588594387], [1548.4572965158027, 241.5523054071067],
[1892.7592776185272, 342.33495115591734], [2254.5289081772476,
445.98514873992008], [2656.9656149224697, 571.79649071207928],
[2971.1562661999892, 867.70244034080304], [3068.3911866286853,
1286.0266095582174], [2929.8340389691793, 1672.0031179683222],
[2613.8132245402226, 1903.4008185146297], [2238.0791358590532,
1946.1114436655755], [1891.3179056028878, 1862.0534199001079],
[1575.3878471688531, 1818.865481764926], [1287.8256402921395,
1766.8583248583836], [1026.4040596301347, 1702.4873909751091],
[783.93932060128668, 1640.5323348318664], [560.42180223554942,
1588.6583330557301], [354.57960965335764, 1540.1880782707833],
[164.40489058630092, 1498.9624158157519]], "imsize": [3264, 2448]},
"43": {"loc": [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17],
"pts": [[986.9522062723704, 697.0146815449186], [1178.2569415526625,
664.0692929800059], [1360.425560676298, 662.1313289467757],
[1526.8136155293448, 681.7878212838245], [1683.2349982114938,
697.2915335496658], [1827.4748926847676, 710.8572817822769],
[1962.0249669918903, 720.2702499436805], [2086.054665118621,
725.8072900386238], [2203.7167671361667, 730.7906261240727],
[2313.903865025539, 730.7906261240728], [2417.1696627962324,
733.2822941667973], [2513.2373084434994, 760.4137906320195],
[2603.7679139958227, 795.2971432301624], [2689.5920354674445,
829.0730878093167], [2769.3254128346284, 857.0351402887804],
[2840.4763780546505, 917.1120253189156], [2882.55788277622,
1023.4231951418275]], "imsize": [3264, 2448]},
"47": {"loc": [34, 35, 36], "pts": [[1393.0609259457722,
1700.979369842461], [1193.0180580859501, 1746.2349694566501],
[957.55776444111029, 1801.984621155289]],
"imsize": [3264, 2448]}}"""}]
I tried this:
test = test[0]
a = test[0].pts
print test
print a #not print a
If you want to change the value of points into a dict that you can parse try:
points = eval(test[0]['pts'])
this will make points equal to:
{'47': {'loc': [34, 35, 36],
'pts': [[1393.0609259457722, 1700.979369842461], [1193.01805808595, 1746.23496945665], [957.5577644411103, 1801.984621155289]],
'imsize': [3264, 2448]},
'2': {'loc': [11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32],
'pts': [[238.12358231315642, 253.66068427891196], [458.64277680287756, 241.96368624623565], [697.0152840793153, 227.18853083653903], [958.1661559457013, 201.82451404989325], [1246.281686434784, 203.42515588594387], [1548.4572965158027, 241.5523054071067], [1892.7592776185272, 342.33495115591734], [2254.5289081772476, 445.9851487399201], [2656.9656149224697, 571.7964907120793], [2971.156266199989, 867.702440340803], [3068.3911866286853, 1286.0266095582174], [2929.8340389691793, 1672.0031179683222], [2613.8132245402226, 1903.4008185146297], [2238.079135859053, 1946.1114436655755], [1891.3179056028878, 1862.0534199001079], [1575.387847168853, 1818.865481764926], [1287.8256402921395, 1766.8583248583836], [1026.4040596301347, 1702.487390975109], [783.9393206012867, 1640.5323348318664], [560.4218022355494, 1588.65833305573], [354.57960965335764, 1540.1880782707833], [164.40489058630092, 1498.962415815752]],
'imsize': [3264, 2448]},
'43': {'loc': [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17],
'pts': [[986.9522062723704, 697.0146815449186], [1178.2569415526625, 664.0692929800059],[1360.425560676298, 662.1313289467757], [1526.8136155293448, 681.7878212838245],[1683.2349982114938, 697.2915335496658], [1827.4748926847676, 710.8572817822769],[1962.0249669918903, 720.2702499436805], [2086.054665118621, 725.8072900386238],[2203.7167671361667, 730.7906261240727], [2313.903865025539, 730.7906261240728],[2417.1696627962324, 733.2822941667973], [2513.2373084434994, 760.4137906320195],[2603.7679139958227, 795.2971432301624], [2689.5920354674445, 829.0730878093167],[2769.3254128346284, 857.0351402887804], [2840.4763780546505, 917.1120253189156],[2882.55788277622, 1023.4231951418275]],
'imsize': [3264, 2448]}
}
You can then get each of those dicts by the keys points['47'],points['2'], or points['43'].
Instead try
print test[0]['pts']
as you need to use the key here.
I think it's a little unclear what you're asking.
It looks like you have a list of dictionaries, and you only care about the first element of the list, whose key is pts. Then you want to do something with the dictionary key. The dictionary key appears ti be a JSON string, so you'll need to decode it. Try the following, to get started:
from pprint import pprint
import json
test = [{'pts': u"""{"2": {"loc": [11, 12, 13, 14, 15, 16, 17, 18, 19, 20,
21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32], "pts": [[
238.12358231315642, 253.66068427891196], [458.64277680287756,
241.96368624623565], [697.01528407931528, 227.18853083653903],
[958.16615594570135, 201.82451404989325], [1246.281686434784,
203.42515588594387], [1548.4572965158027, 241.5523054071067],
[1892.7592776185272, 342.33495115591734], [2254.5289081772476,
445.98514873992008], [2656.9656149224697, 571.79649071207928],
[2971.1562661999892, 867.70244034080304], [3068.3911866286853,
1286.0266095582174], [2929.8340389691793, 1672.0031179683222],
[2613.8132245402226, 1903.4008185146297], [2238.0791358590532,
1946.1114436655755], [1891.3179056028878, 1862.0534199001079],
[1575.3878471688531, 1818.865481764926], [1287.8256402921395,
1766.8583248583836], [1026.4040596301347, 1702.4873909751091],
[783.93932060128668, 1640.5323348318664], [560.42180223554942,
1588.6583330557301], [354.57960965335764, 1540.1880782707833],
[164.40489058630092, 1498.9624158157519]], "imsize": [3264, 2448]},
"43": {"loc": [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17],
"pts": [[986.9522062723704, 697.0146815449186], [1178.2569415526625,
664.0692929800059], [1360.425560676298, 662.1313289467757],
[1526.8136155293448, 681.7878212838245], [1683.2349982114938,
697.2915335496658], [1827.4748926847676, 710.8572817822769],
[1962.0249669918903, 720.2702499436805], [2086.054665118621,
725.8072900386238], [2203.7167671361667, 730.7906261240727],
[2313.903865025539, 730.7906261240728], [2417.1696627962324,
733.2822941667973], [2513.2373084434994, 760.4137906320195],
[2603.7679139958227, 795.2971432301624], [2689.5920354674445,
829.0730878093167], [2769.3254128346284, 857.0351402887804],
[2840.4763780546505, 917.1120253189156], [2882.55788277622,
1023.4231951418275]], "imsize": [3264, 2448]},
"47": {"loc": [34, 35, 36], "pts": [[1393.0609259457722,
1700.979369842461], [1193.0180580859501, 1746.2349694566501],
[957.55776444111029, 1801.984621155289]],
"imsize": [3264, 2448]}}"""}]
# Print the original input (it's a list of dictionaries that map keys to JSON strings)
pprint(test)
pts = json.loads(test[0]['pts'])
# Print the decoded JSON.
pprint(pts)