pyth_15_series
Заметка 15. Pandas Series.
курса Математический практикум по Питону.
Шокуров Антон В.
shokurov.anton.v@yandex.ru
http://машинноезрение.рф
Версия 0.11

Аннотация

Pandas таблицы. Столбцы. Series. Серии.

Это предварительная версия! Любые замечания приветсвуются.

In [1]:
import numpy as np
import matplotlib.pyplot as plt

import scipy.stats as models

Работа с таблицами

Введение

Загрузка через csv

In [2]:
import csv
In [3]:
data = []
with open( 'MTLR_180101_190110.txt' ) as f:
    data_rows = csv.reader( f, delimiter = ';' )
    data = list( data_rows )

Мы должны помнить о том, что второй с конца столбец отвечает за цену закрытия.

In [4]:
close = list( map( lambda x: float(x[-2]), data) ) # Здесь мы должны знать, что -2 это то что нужно.
In [5]:
plt.plot( close )
plt.ylabel( 'Цена рубли')
plt.xlabel( 'День начиная с 2018 г')
plt.legend(['Цена ВТБ']) # Соответсвенно помнить название жмитента.
Out[5]:
<matplotlib.legend.Legend at 0x7f8b3ce67cf8>

Можно было создать класс, который все это помнит. Но зачем, если уже за нас это сделали?

Для более аккуратной работы с данными есть модуль pandas.

Подключаем pandas

In [6]:
import pandas as pd # Загружаем модуль pandas под псевдонимом pd.

Начнем с загрузки простого файла, т.е. небольшого развера.

In [7]:
mtlr_df = pd.read_csv('MTLR_190101_190110.txt', sep = ';') # Считываем данные из файла.
mtlr_df
Out[7]:
MTLR D 20190103 000000 73.8900000 74.4700000 73.0600000 73.1200000 391375
0 MTLR D 20190104 0 73.31 74.89 73.21 73.68 462658
1 MTLR D 20190108 0 74.47 74.89 73.50 73.74 406304
2 MTLR D 20190109 0 74.02 74.62 73.82 73.93 651998
3 MTLR D 20190110 0 73.96 74.78 73.90 74.40 358269

Хм.. Как мы видим у колонок появились названия. Но они какие-то не те.

In [8]:
# headerr = None указывает, что заголовка в файле нет.
mtlr_df = pd.read_csv('MTLR_190101_190110.txt', sep = ';', header = None)
mtlr_df
Out[8]:
0 1 2 3 4 5 6 7 8
0 MTLR D 20190103 0 73.89 74.47 73.06 73.12 391375
1 MTLR D 20190104 0 73.31 74.89 73.21 73.68 462658
2 MTLR D 20190108 0 74.47 74.89 73.50 73.74 406304
3 MTLR D 20190109 0 74.02 74.62 73.82 73.93 651998
4 MTLR D 20190110 0 73.96 74.78 73.90 74.40 358269

Теперь колонки получили иемя, правда цифровое, т.е. они пронумированы.

Загрузим данные заново (например с сайта finam), но теперь убедися что стоит флажок у "Добавить заголовок файла"

In [9]:
mtlr_df = pd.read_csv('MTLR_190101_190110_header.txt', sep = ';') # Считываем данные из файла включая заголовок.
mtlr_df
Out[9]:
<TICKER> <PER> <DATE> <TIME> <OPEN> <HIGH> <LOW> <CLOSE> <VOL>
0 MTLR D 20190103 0 73.89 74.47 73.06 73.12 391375
1 MTLR D 20190104 0 73.31 74.89 73.21 73.68 462658
2 MTLR D 20190108 0 74.47 74.89 73.50 73.74 406304
3 MTLR D 20190109 0 74.02 74.62 73.82 73.93 651998
4 MTLR D 20190110 0 73.96 74.78 73.90 74.44 475643

Как мы видми у колонок появились правильные названия.

Изменение именования колонок

В любом случае мы возможно хотим переименовать название колонок. Либо пронумерованных, либо англоязычных.

In [10]:
mtlr_df.columns # Колонки хранятся в данной переменной таблицы пандас.
Out[10]:
Index(['<TICKER>', '<PER>', '<DATE>', '<TIME>', '<OPEN>', '<HIGH>', '<LOW>',
       '<CLOSE>', '<VOL>'],
      dtype='object')
In [11]:
len(mtlr_df.columns) # Количество колнок.
Out[11]:
9
In [12]:
mtlr_df.columns = ['Эмитент', 'Процент', 'Дата', 'Время', 'Открытие', 'Максимум', 'Минимум', 'Закрытие', 'Обьем']
In [13]:
mtlr_df.columns # Не список уже!
Out[13]:
Index(['Эмитент', 'Процент', 'Дата', 'Время', 'Открытие', 'Максимум',
       'Минимум', 'Закрытие', 'Обьем'],
      dtype='object')
In [14]:
mtlr_df # Появились нормальные названия колонок.
Out[14]:
Эмитент Процент Дата Время Открытие Максимум Минимум Закрытие Обьем
0 MTLR D 20190103 0 73.89 74.47 73.06 73.12 391375
1 MTLR D 20190104 0 73.31 74.89 73.21 73.68 462658
2 MTLR D 20190108 0 74.47 74.89 73.50 73.74 406304
3 MTLR D 20190109 0 74.02 74.62 73.82 73.93 651998
4 MTLR D 20190110 0 73.96 74.78 73.90 74.44 475643
In [15]:
# Разумеется нужно следить за количеством колонок.
mtlr_df.columns = ['Открытие', 'Максимум', 'Минимум', 'Закрытие', 'Обьем']
---------------------------------------------------------------------------
ValueError                                Traceback (most recent call last)
<ipython-input-15-7b672edf5297> in <module>
      1 # Разумеется нужно следить за количеством колонок.
----> 2 mtlr_df.columns = ['Открытие', 'Максимум', 'Минимум', 'Закрытие', 'Обьем']

/data/conda/anaconda3/envs/data_analysis/lib/python3.6/site-packages/pandas/core/generic.py in __setattr__(self, name, value)
   5068         try:
   5069             object.__getattribute__(self, name)
-> 5070             return object.__setattr__(self, name, value)
   5071         except AttributeError:
   5072             pass

pandas/_libs/properties.pyx in pandas._libs.properties.AxisProperty.__set__()

/data/conda/anaconda3/envs/data_analysis/lib/python3.6/site-packages/pandas/core/generic.py in _set_axis(self, axis, labels)
    627 
    628     def _set_axis(self, axis, labels):
--> 629         self._data.set_axis(axis, labels)
    630         self._clear_item_cache()
    631 

/data/conda/anaconda3/envs/data_analysis/lib/python3.6/site-packages/pandas/core/internals/managers.py in set_axis(self, axis, new_labels)
    153             raise ValueError(
    154                 'Length mismatch: Expected axis has {old} elements, new '
--> 155                 'values have {new} elements'.format(old=old_len, new=new_len))
    156 
    157         self.axes[axis] = new_labels

ValueError: Length mismatch: Expected axis has 9 elements, new values have 5 elements

Таблица

Вообще, что за объект, который мы загрузили?

In [16]:
type(mtlr_df) # Объект типа DataFrame
Out[16]:
pandas.core.frame.DataFrame
In [17]:
my_close = mtlr_df['Закрытие'] # Можно из таблицы извлесь колонку.
my_close
Out[17]:
0    73.12
1    73.68
2    73.74
3    73.93
4    74.44
Name: Закрытие, dtype: float64
In [18]:
type(my_close) # Тип у колонки Series, т.е. серия.
Out[18]:
pandas.core.series.Series

И вот сначала мы обсудим тип Series, т.е. что можно делать с колонкой.

Серия

Перейдем к обсуждению объекта Серия (Series) модуля Pandas.

Объект

Создание, удаление

In [19]:
new_ser = pd.Series([50, 100, 75, 23]) # Создаем Серию по списку.
new_ser
Out[19]:
0     50
1    100
2     75
3     23
dtype: int64
In [20]:
type( new_ser )
Out[20]:
pandas.core.series.Series

Пандас достаточно мудрен, чтобы выбрать наилучший тип для данных. Так если все данные целые, то и итоговые тип будет целым.

In [21]:
new_ser.dtype # Обращу внимание, что тип целочисленный. В этом смысле Пандас умничает.
Out[21]:
dtype('int64')

Если хотя бы одно число действительное, то и тоговая таблица будет такой.

In [22]:
new_serf = pd.Series([50, -100, -75., 23])
new_serf # В данном случае тип float64, т.е. действительные.
Out[22]:
0     50.0
1   -100.0
2    -75.0
3     23.0
dtype: float64
In [23]:
new_sers = pd.Series(['Москва', 'Питер', 'Нижний', 'Новосибирск']) # Можно хранить и произвольные объекты.
new_sers # Например, строчки, но тогда тип будет object
Out[23]:
0         Москва
1          Питер
2         Нижний
3    Новосибирск
dtype: object

В предыдущих примерах первая колонка добавлялась автоматически. Она называется индексом. Поумолчанию она цифровая, т.е. индекс целочисленный. Но можно идекс задать и в явном виде.

In [24]:
cptls = pd.Series([1,4,7,8], index=['Москва', 'Питер', 'Нижний', 'Новосибирск'])
cptls # Индекс к тому же и не числовой.
Out[24]:
Москва         1
Питер          4
Нижний         7
Новосибирск    8
dtype: int64

Просмотр

In [25]:
cptls.values
Out[25]:
array([1, 4, 7, 8])
In [26]:
cptls.index
Out[26]:
Index(['Москва', 'Питер', 'Нижний', 'Новосибирск'], dtype='object')
In [27]:
list( cptls.iteritems() )
Out[27]:
[('Москва', 1), ('Питер', 4), ('Нижний', 7), ('Новосибирск', 8)]
In [28]:
cptls.keys()
Out[28]:
Index(['Москва', 'Питер', 'Нижний', 'Новосибирск'], dtype='object')

Операции

Операции как над массивами

In [29]:
my_close # Еще раз его выведем.
Out[29]:
0    73.12
1    73.68
2    73.74
3    73.93
4    74.44
Name: Закрытие, dtype: float64
In [30]:
my_close*2 # Можно оперировать как с массивом из Numpy.
Out[30]:
0    146.24
1    147.36
2    147.48
3    147.86
4    148.88
Name: Закрытие, dtype: float64
In [31]:
new_serf.abs() # Взяли абсолютную величину от всех значений.
Out[31]:
0     50.0
1    100.0
2     75.0
3     23.0
dtype: float64
In [32]:
my_open = mtlr_df['Открытие'] # Извлечем ещё и цену открытия.
my_open
Out[32]:
0    73.89
1    73.31
2    74.47
3    74.02
4    73.96
Name: Открытие, dtype: float64
In [33]:
avg = 0.5*(my_close + my_open) # Нашли среднее двух колонок.
avg
Out[33]:
0    73.505
1    73.495
2    74.105
3    73.975
4    74.200
dtype: float64
In [34]:
type( avg ) # Мы по прежнему остаемся в рамка Серии.
Out[34]:
pandas.core.series.Series
In [35]:
my_open
Out[35]:
0    73.89
1    73.31
2    74.47
3    74.02
4    73.96
Name: Открытие, dtype: float64
In [36]:
my_close.corr(my_open) # cov
Out[36]:
0.12696695817210182

Интегральные операции

In [37]:
my_close.mean(), my_open.max()
Out[37]:
(73.78200000000001, 74.47)

Как над списками

In [38]:
my_app = my_open.append( my_close ) # Напомню что в array нельзя добавлять новые элименты.
my_app # Но что произошло с индексом? Он тоже добавился.
Out[38]:
0    73.89
1    73.31
2    74.47
3    74.02
4    73.96
0    73.12
1    73.68
2    73.74
3    73.93
4    74.44
dtype: float64
In [39]:
cptls
Out[39]:
Москва         1
Питер          4
Нижний         7
Новосибирск    8
dtype: int64
In [40]:
del cptls['Нижний']
In [41]:
cptls
Out[41]:
Москва         1
Питер          4
Новосибирск    8
dtype: int64

Значения можети не быть

In [42]:
nums = [5, 6, None, 10] # Список значений и пустота.
nums
Out[42]:
[5, 6, None, 10]
In [43]:
a = np.array( nums )
a # Тип object!
Out[43]:
array([5, 6, None, 10], dtype=object)
In [44]:
a*2 # Такое не прокатит.
---------------------------------------------------------------------------
TypeError                                 Traceback (most recent call last)
<ipython-input-44-7a9d19fccd96> in <module>
----> 1 a*2 # Такое не прокатит.

TypeError: unsupported operand type(s) for *: 'NoneType' and 'int'
In [45]:
nums_ser = pd.Series( nums )
nums_ser # Тип всеравно float64!
Out[45]:
0     5.0
1     6.0
2     NaN
3    10.0
dtype: float64
In [46]:
nums_ser * 2 # Nan проигнорирован.
Out[46]:
0    10.0
1    12.0
2     NaN
3    20.0
dtype: float64
In [47]:
nums_ser.count() # Количество реальных данных.
Out[47]:
3
In [48]:
nums_ser.mean() # Правильно считает среднее. 5+6+10=21 => 21/3 = 7.0
Out[48]:
7.0
In [49]:
nums_ser.describe()
Out[49]:
count     3.000000
mean      7.000000
std       2.645751
min       5.000000
25%       5.500000
50%       6.000000
75%       8.000000
max      10.000000
dtype: float64
In [50]:
nums_ser.dropna() # Оставляем строки со значением.
Out[50]:
0     5.0
1     6.0
3    10.0
dtype: float64
In [51]:
nums_ser.fillna(-1)
Out[51]:
0     5.0
1     6.0
2    -1.0
3    10.0
dtype: float64

Принадлежность

In [52]:
cptls
Out[52]:
Москва         1
Питер          4
Новосибирск    8
dtype: int64
In [53]:
'Москва' in cptls, 'Британия' in cptls
Out[53]:
(True, False)

Обновить значение

In [54]:
cptls['Екатеринбург'] = 55
In [55]:
cptls
Out[55]:
Москва           1
Питер            4
Новосибирск      8
Екатеринбург    55
dtype: int64
In [56]:
cptls['Нижний'] = 11
cptls
Out[56]:
Москва           1
Питер            4
Новосибирск      8
Екатеринбург    55
Нижний          11
dtype: int64
In [57]:
cptls.get('Владивосток', 'не известно')
Out[57]:
'не известно'
In [58]:
#cptls.

Индексирование

Как у массива

In [59]:
new_ser[2] # Для Серии действуют теже правила как и для массива. Важно что это число!
Out[59]:
75
In [60]:
new_ser[1:-1] # Извлечь с первого по невключительно последний элемент. Важно что это Серия!
Out[60]:
1    100
2     75
dtype: int64

Последние два примеры важны. Если не учитывать, то код может сломаться.

In [61]:
my_app # Помним про данную Серию?
Out[61]:
0    73.89
1    73.31
2    74.47
3    74.02
4    73.96
0    73.12
1    73.68
2    73.74
3    73.93
4    74.44
dtype: float64
In [62]:
my_app[2] # Раз индекс продублирован, то два элемента, т.е. опять Серия.
Out[62]:
2    74.47
2    73.74
dtype: float64

Не числовой индекс

In [63]:
cptls
Out[63]:
Москва           1
Питер            4
Новосибирск      8
Екатеринбург    55
Нижний          11
dtype: int64
In [64]:
cptls['Москва']
Out[64]:
1

Педантизм

In [65]:
tt = pd.Series(['a','b','c','d'], index=[2,1,3,0])
tt
Out[65]:
2    a
1    b
3    c
0    d
dtype: object
In [66]:
tt[0] # Что будет? Что хотели?
Out[66]:
'd'
In [67]:
tt.iloc[0] # Является номером строки.
Out[67]:
'a'
In [68]:
tt.iloc[2]
Out[68]:
'c'
In [69]:
tt.loc[2] # Всегда соответствует названию элемента индекса.
Out[69]:
'a'
In [70]:
#new_cptls = pd.Series(['Москва','Париж','Рим','Берлин'], index=['Россия','Франция','Италия','Германия'])
In [71]:
cptls[1] # Вернет как номер строчки.
Out[71]:
4
In [72]:
cptls.iloc[1] # Тоже самое.
Out[72]:
4
In [73]:
cptls.loc['Москва']
Out[73]:
1
In [74]:
cptls.loc[1] # Так нельзя. Нужно обазательно элемент индекса, т.е. название.
---------------------------------------------------------------------------
TypeError                                 Traceback (most recent call last)
<ipython-input-74-e28a5381aa1e> in <module>
----> 1 cptls.loc[1] # Так нельзя. Нужно обазательно элемент индекса, т.е. название.

/data/conda/anaconda3/envs/data_analysis/lib/python3.6/site-packages/pandas/core/indexing.py in __getitem__(self, key)
   1499 
   1500             maybe_callable = com.apply_if_callable(key, self.obj)
-> 1501             return self._getitem_axis(maybe_callable, axis=axis)
   1502 
   1503     def _is_scalar_access(self, key):

/data/conda/anaconda3/envs/data_analysis/lib/python3.6/site-packages/pandas/core/indexing.py in _getitem_axis(self, key, axis)
   1911 
   1912         # fall thru to straight lookup
-> 1913         self._validate_key(key, axis)
   1914         return self._get_label(key, axis=axis)
   1915 

/data/conda/anaconda3/envs/data_analysis/lib/python3.6/site-packages/pandas/core/indexing.py in _validate_key(self, key, axis)
   1798 
   1799         if not is_list_like_indexer(key):
-> 1800             self._convert_scalar_indexer(key, axis)
   1801 
   1802     def _is_scalar_access(self, key):

/data/conda/anaconda3/envs/data_analysis/lib/python3.6/site-packages/pandas/core/indexing.py in _convert_scalar_indexer(self, key, axis)
    260         ax = self.obj._get_axis(min(axis, self.ndim - 1))
    261         # a scalar
--> 262         return ax._convert_scalar_indexer(key, kind=self.name)
    263 
    264     def _convert_slice_indexer(self, key, axis):

/data/conda/anaconda3/envs/data_analysis/lib/python3.6/site-packages/pandas/core/indexes/base.py in _convert_scalar_indexer(self, key, kind)
   2799             elif kind in ['loc'] and is_integer(key):
   2800                 if not self.holds_integer():
-> 2801                     return self._invalid_indexer('label', key)
   2802 
   2803         return key

/data/conda/anaconda3/envs/data_analysis/lib/python3.6/site-packages/pandas/core/indexes/base.py in _invalid_indexer(self, form, key)
   2985                         "indexers [{key}] of {kind}".format(
   2986                             form=form, klass=type(self), key=key,
-> 2987                             kind=type(key)))
   2988 
   2989     # --------------------------------------------------------------------

TypeError: cannot do label indexing on <class 'pandas.core.indexes.base.Index'> with these indexers [1] of <class 'int'>
In [75]:
cptls.loc['Питер':]
Out[75]:
Питер            4
Новосибирск      8
Екатеринбург    55
Нижний          11
dtype: int64
In [76]:
dd = pd.Series( [1, 2, 1, 4], index=[11, 15, 20, 25])
In [77]:
dd.iat[2]
Out[77]:
1

Атрибут

In [78]:
cptls.Москва
Out[78]:
1

Булевские

In [79]:
a = pd.Series([55, 33, 88, 11])
b = pd.Series([44, 22, 100, 22])
In [80]:
a<b # По аналогии с другими операциями на сериями.
Out[80]:
0    False
1    False
2     True
3     True
dtype: bool
In [81]:
a[a<b] # Используем Серию в качестве фильтра.
Out[81]:
2    88
3    11
dtype: int64

Индекс, как с ним быть

Изучим что есть

In [82]:
my_app
Out[82]:
0    73.89
1    73.31
2    74.47
3    74.02
4    73.96
0    73.12
1    73.68
2    73.74
3    73.93
4    74.44
dtype: float64
In [83]:
my_app.index
Out[83]:
Int64Index([0, 1, 2, 3, 4, 0, 1, 2, 3, 4], dtype='int64')
In [84]:
a.index
Out[84]:
RangeIndex(start=0, stop=4, step=1)

Новый

In [85]:
rr = my_app.reset_index() # Для создания нового индекса.
rr # Теперь выглядит как таблица. Старый индекс превращен в колонку.
Out[85]:
index 0
0 0 73.89
1 1 73.31
2 2 74.47
3 3 74.02
4 4 73.96
5 0 73.12
6 1 73.68
7 2 73.74
8 3 73.93
9 4 74.44
In [86]:
rr.index.is_unique
Out[86]:
True

Нужен новый индекс. По хорошему индекс должен однозначно определять строчку.

In [87]:
type(rr) # И действительно это DataFrame. Иногда это нужно, но не сейчас.
Out[87]:
pandas.core.frame.DataFrame
In [88]:
rr = my_app.reset_index( drop = True) # Для затирания старого "индекса"
rr
Out[88]:
0    73.89
1    73.31
2    74.47
3    74.02
4    73.96
5    73.12
6    73.68
7    73.74
8    73.93
9    74.44
dtype: float64
In [89]:
type(rr) # Да это Серия.
Out[89]:
pandas.core.series.Series
In [90]:
rr[2] # Теперь однозначность опять есть.
Out[90]:
74.47
In [91]:
a
Out[91]:
0    55
1    33
2    88
3    11
dtype: int64
In [92]:
a.index = ['a', 'b', 'c', 'd'] # Можно и так.
In [93]:
a
Out[93]:
a    55
b    33
c    88
d    11
dtype: int64

Сортировка

In [94]:
cptls
Out[94]:
Москва           1
Питер            4
Новосибирск      8
Екатеринбург    55
Нижний          11
dtype: int64
In [95]:
cptls.sort_index()
Out[95]:
Екатеринбург    55
Москва           1
Нижний          11
Новосибирск      8
Питер            4
dtype: int64
In [96]:
cptls.sort_values()
Out[96]:
Москва           1
Питер            4
Новосибирск      8
Нижний          11
Екатеринбург    55
dtype: int64
In [97]:
cptls.rank()
Out[97]:
Москва          1.0
Питер           2.0
Новосибирск     3.0
Екатеринбург    5.0
Нижний          4.0
dtype: float64

Произвольные вычисления

In [98]:
a
Out[98]:
a    55
b    33
c    88
d    11
dtype: int64
In [99]:
a.map( lambda x: x*x )
Out[99]:
a    3025
b    1089
c    7744
d     121
dtype: int64
In [100]:
a.map( {55:'a', 33:'b', 88:'d'} )
Out[100]:
a      a
b      b
c      d
d    NaN
dtype: object
In [101]:
a
Out[101]:
a    55
b    33
c    88
d    11
dtype: int64
In [102]:
#a.apply( {55:'a', 33:'b', 88:'d'} )
In [103]:
aa = pd.Series([1,5,-2])
bb = pd.Series([-2,7,3, 4])
In [104]:
aa
Out[104]:
0    1
1    5
2   -2
dtype: int64
In [105]:
bb
Out[105]:
0   -2
1    7
2    3
3    4
dtype: int64
In [106]:
aa.combine(bb, lambda x, y: x*y)
Out[106]:
0    -2.0
1    35.0
2    -6.0
3     NaN
dtype: float64
In [107]:
aa = pd.Series([1,5,-2], index=[2,3,4])
aa
Out[107]:
2    1
3    5
4   -2
dtype: int64
In [108]:
aa.combine(bb, lambda x, y: x*y)
Out[108]:
0     NaN
1     NaN
2     3.0
3    20.0
4     NaN
dtype: float64

Группы

In [109]:
grades = pd.Series([30,20,25, 55, 60, 40, 30, 40, 45],
                   index=['Максим','Максим','Максим',
                         'Аня', 'Аня', 'Аня',
                         'Дима', 'Дима', 'Дима'])
grades
Out[109]:
Максим    30
Максим    20
Максим    25
Аня       55
Аня       60
Аня       40
Дима      30
Дима      40
Дима      45
dtype: int64
In [110]:
grades.groupby(by=grades.index).mean()
Out[110]:
Аня       51.666667
Дима      38.333333
Максим    25.000000
dtype: float64

Поиск

In [111]:
my_open.where( lambda x: x>74 )
Out[111]:
0      NaN
1      NaN
2    74.47
3    74.02
4      NaN
Name: Открытие, dtype: float64
In [112]:
#my_open.asfreq(0.5)
In [50]:
my_open.c
---------------------------------------------------------------------------
AttributeError                            Traceback (most recent call last)
<ipython-input-50-e07ed182bc4e> in <module>
----> 1 my_open.c

/data/conda/anaconda3/envs/data_analysis/lib/python3.6/site-packages/pandas/core/generic.py in __getattr__(self, name)
   5055             if self._info_axis._can_hold_identifiers_and_holds_name(name):
   5056                 return self[name]
-> 5057             return object.__getattribute__(self, name)
   5058 
   5059     def __setattr__(self, name, value):

AttributeError: 'Series' object has no attribute 'c'
In [51]:
my_open.groupby( lambda x: int(x) )
Out[51]:
<pandas.core.groupby.generic.SeriesGroupBy object at 0x7fbdbce97a20>
In [52]:
my_open
Out[52]:
0    73.89
1    73.31
2    74.47
3    74.02
4    73.96
Name: Открытие, dtype: float64
In [53]:
my_open.reindex(index=['день один', 'день два', 'день три', 'день четыре','dd','aa','aaqq'])
Out[53]:
день один     NaN
день два      NaN
день три      NaN
день четыре   NaN
dd            NaN
aa            NaN
aaqq          NaN
Name: Открытие, dtype: float64
In [ ]:
 
In [ ]:
tmp_col = my_open.copy()