Anthony W
Anthony W

Reputation: 1327

Pandas repeated values

Is there a more idiomatic way of doing this in Pandas?

I want to set-up a column that repeats the integers 1 to 48, for an index of length 2000:

df = pd.DataFrame(np.zeros((2000, 1)), columns=['HH'])
h = 1

for i in range(0,2000) :
    df.loc[i,'HH'] = h
    if h >=48 : h =1
    else : h += 1

Upvotes: 0

Views: 88

Answers (2)

danielhadar
danielhadar

Reputation: 2161

df = pd.DataFrame({'HH':np.append(np.tile(range(1,49),int(2000/48)), range(1,np.mod(2000,48)+1))})

That is, appending 2 arrays:

(1) np.tile(range(1,49),int(2000/48))

len(np.tile(range(1,49),int(2000/48)))
1968

(2) range(1,np.mod(2000,48)+1)

len(range(1,np.mod(2000,48)+1))
32

And constructing the DataFrame from a corresponding dictionary.

Upvotes: 0

Holt
Holt

Reputation: 37606

Here is more direct and faster way:

pd.DataFrame(np.tile(np.arange(1, 49), 2000 // 48 + 1)[:2000], columns=['HH'])

The detailed step:

  1. np.arange(1, 49) creates an array from 1 to 48 (included)
>>> l = np.arange(1, 49)
>>> l
array([ 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])
  1. np.tile(A, N) repeats the array A N times, so in this case you get [1 2 3 ... 48 1 2 3 ... 48 ... 1 2 3 ... 48]. You should repeat the array 2000 // 48 + 1 times in order to get at least 2000 values.
>>> r = np.tile(l, 2000 // 48 + 1)
>>> r
array([ 1,  2,  3, ..., 46, 47, 48])
>>> r.shape # The array is slightly larger than 2000
(2016,)
  1. [:2000] retrieves the 2000 first values from the generated array to create your DataFrame.
>>> d = pd.DataFrame(r[:2000], columns=['HH'])

Upvotes: 3

Related Questions