简体   繁体   中英

numpy array vs list of lists?

EDIT: I have changed np.array to np.arange to better explain what my problem is.

Being new to Python, I still struggle a lot with data structures. This seems like it should be a very obvious (and obviously duplicate) question, yet I can't understand enough of other explanations to make it work.

I need to create a list of lists (and / or arrays, I'll explain this in a minute), all with different lengths and ranges. I set up my initial arrays in the following way, but I still don't understand how to create the 'partotal' array. I know the syntax is wrong but still don't understand why.

import numpy as np

par1 = np.arange([10,80,1])
par2 = np.arange([50,120,1])
par3 = np.arange([0,40,1])
par4 = np.arange([0,30,1])

partotal = np.array([par1][par2][par3][par4])

The second problem, as you may have guessed, is that I have no idea whether I should be using numpy arrays, list of lists, pandas, or something else entirely. Since all my arrays are of different lengths, I find it hard to understand how to put things together or remove them again.

EDIT: The purpose of partotal is to create a set of starting positions for another function (see below)

inputnumber = 200

def positions(partotal, inputnumber):
    return np.random.uniform(partotal, size=(inputnumber, len(partotal)))

I know this must sound very basic but as a beginner I find it confusing and difficult. Most answers focus on syntax and don't help develop true insight. If someone can take some time to explain the very obvious I would appreciate it.

FINAL EDIT: The answer was very simple when I understood my own problem. I won't delete the rest of the post, for the sake of others who might need to follow my thought process.

par = 3
par1 = np.random.uniform(10,80,size=par)
par2 = np.random.uniform(5,120,size=par)
par3 = np.random.uniform(0,40,size=par)

allpar = np.array([par1,par2,par3])

If you're trying to create a 2d array you can just pass a 2d list to np.array .

np.array([[10, 80, 1], [50, 120, 1], [0, 40, 1], [0, 30, 1]])

Not sure if this is what you're going for, but in your specific case you'd do:

partotal = np.array([par1, par2, par3, par4])

A common use of uniform is to specify scalar start and stop values, and a shape:

In [101]: np.random.uniform(0,1,size=(3,4))
Out[101]: 
array([[0.87953793, 0.83726369, 0.53280941, 0.69611469],
       [0.78369061, 0.99258945, 0.65533223, 0.8342177 ],
       [0.69943211, 0.53965698, 0.06419811, 0.36591087]])

This is 12 values drawn from [0,1), arranged in a (3,4) array.

It's docs says that start and stop can be arrays, but isn't very clear about how they are used. The best clue is in:

np.broadcast(low, high).size samples are drawn.

So trying (3,1) and (1,4) inputs, we again get a (3,4) array.

In [102]: np.random.uniform(np.zeros((3,1)), np.ones((1,4)))
Out[102]: 
array([[0.35865707, 0.39068231, 0.9117642 , 0.49346499],
       [0.1439195 , 0.1217748 , 0.21780452, 0.83235673],
       [0.24894503, 0.36413268, 0.51516651, 0.8480244 ]])

To generate 3 numbers from (0,1), (10,11), and (20,21) respectively:

In [105]: np.random.uniform(np.arange(0,30,10), np.arange(1,31,10))
Out[105]: array([ 0.54715093, 10.75390957, 20.98101312])

I don't know what you are trying to do with those 4 arrays.

In [107]: par1 = np.arange(10,80)     # corrected usage
     ...: par2 = np.arange(50,120)
     ...: par3 = np.arange(0,40)
     ...: par4 = np.arange(0,30)

I could concatenate those 4 arrays into one:

In [108]: par = np.concatenate([par1,par2,par3,par4])
In [109]: par.shape
Out[109]: (210,)

With different lengths, this hstack is the only option.

Notice that I constructed a list of those arrays, and used that as an input to concatenate (as it expected).

In [110]: alist = [par1,par2,par3,par4]

A list of lists or list of arrays is a easy Python construct. It certainly should be used before trying to make an array of arrays (of differing sizes). But I don't see how that applies to uniform (as I just illustrated).

Another (3,4) array of random values:

In [111]: np.random.uniform(np.arange(3)[:,None], np.arange(4))
Out[111]: 
array([[0.        , 0.74651856, 0.60318064, 0.75254649],
       [0.49864947, 1.        , 1.60558937, 2.06444058],
       [1.03298196, 1.80321816, 2.        , 2.3358475 ]])

Each element is taken from a different range

 [0,0) [0,1) [0,2)
 [1,0) [1,1) [1,2)
 [2,0) ...

Thanks everyone for your help on what I realise was an extremely badly worded question. The answer turned out to be quite simple:

val = 4 # or any required number of start points
par1 = np.random.uniform(10,60,size=val)
par2 = np.random.uniform(0,20,size=val)
par3 = np.random.uniform(0,30,size=val)

allpar = np.array([par1,par2,par3])

This gives me an array of the correct values, with the right number of randomly generated points within specified boundaries.

Thanks everyone who contributed.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM