よちよちpython

独習 python/Qpython/Pydroid3/termux

【Python機械学習】pandasの基本的な使い方1

pandasの使い方メモ。
機械学習でほぼ必須といわれるライブラリのひとつ。機械学習でよく使うらしいメソッドにしぼっています。



目次




実行環境


Windows10
Anaconda
Python3.7
JupyterLab



機械学習を行う際はJupyterLabJupyterNotebookが使われることが多いかと思います。
データを表やグラフにして確認しながら進めていく分析作業が重要で、Jupyterを使うとその点が便利にできるからだと思います。
VSCodeやPyCharm、Atom、ターミナルからIpythonとかでも出来ますが、表示が異なったり設定の手間が掛かるので、素直に最初からJupyterNotebookを使うのが楽そうかなと思います。

なお、この記事はJupyterLabで作成したipynbファイルをmarkdownに変換したものをそのまま投稿しております。
DataFrameを実行した箇所は、はてなブログで自動的にマス目のついた表にhtml変換されて表示されており、Jupyterでの実際の表示とは異なっていることを断っておきます。



Pandasとは?


前回はNumpyの基本的な使い方をやりました。Numpyは行列計算など数値演算を高速で行うライブラリです。
PandasはNumpyを利用して動いており、Excelのような表形式でデータを簡単に扱えるライブラリです。
互いに似たようなことが出来ますが、Pandasは表示を重視しているせいなのかNumpyに比べて計算が遅いそうなので、そのあたりを考慮して使い分けをするのが良いようです。



Pandasのインポート


PandasはPythonの標準ライブラリではないので、先にpipやconda等でインストールしておきます。
PandasはNumpyを利用して動いていると書きましたが、NumpyをimportせずともPandas単体のみのインポートで動きます。
しかしデータを扱う際にNumpy配列を使ったり計算させたりすることが多いので、大抵はnumpyとpandasは同時にインポートして使われています。

# 両方インポートします
import numpy as np
import pandas as pd



データ形式 SeriesとDataFrame


Pandasのデータは

  • 一次元のデータ構造になったSeries(シリーズ)
  • 二次元のDataFrame(データフレーム)

のクラスに分かれています。
実際にそれぞれのデータクラスを作ってみてみます。


Seriesクラスの生成


一次元のデータを生成。Seriesクラスに1次元のリストを渡します。

series = pd.Series([1,2,3,4,5])
series
0    1
1    2
2    3
3    4
4    5
dtype: int64

縦に2列で出力され、一番下にはデータのタイプがdtype: int64と表示されています。64ビットのint型。
列の一番左の(0,1,2,3,4)はindexが自動で表示されております。実際のデータは右の列の「1~5」。
0行目に「1」、1行目に「2」・・・と値が入っています。

Series()の頭は大文字


「series()」のように小文字で書いてしまうとAttributeError: module 'pandas' has no attribute 'series'とerrorが出る。



type(データ) 型の確認


通常で型を調べるときと同じく、type(データ)とやると型が調べられます。

type(series)
pandas.core.series.Series

↓ print関数を使うと少し表示が変わります。

print(type(series))
<class 'pandas.core.series.Series'>



shapeで形状の確認


numpyと同じです。

series.shape
(5,)

(5,)となっているので「5行」の1次元。



ndimで次元を確認


Numpyと同様、ndimで配列の次元が確認できます。

series.ndim
1



sizeで全要素数を確認


配列に何個の要素が含まれているかが調べられます。

series.size
5



indexを指定


何のデータか分かるようにindexを指定できます。

series = pd.Series([1,2,3,4,5], index=["Aくん","Bくん","Cくん","Dくん","Eくん"])
series
Aくん    1
Bくん    2
Cくん    3
Dくん    4
Eくん    5
dtype: int64

5つのデータに5つのindexを与えたので上手く行きましたが、互いの個数が合わないとerrorがでます。

仮にindexを6個与えてみれば、次のようなエラーが出ます。
ValueError: Length of passed values is 5, index implies 6



データを変数で代入


リストを変数に格納後、Seriesクラスに渡してみます。

# リスト
data = ["あ","い","う","え","お"]
index=["Aくん","Bくん","Cくん","Dくん","Eくん"]

# Seriesクラスにdataとindexを代入
series = pd.Series(
    data, 
    index 
)

series
Aくん    あ
Bくん    い
Cくん    う
Dくん    え
Eくん    お
dtype: object

Seriesクラスに変数でリストを渡しました。リストの中身を文字列にしたのでデータのタイプがdtype: objectに変化しています。
()内は見やすく上のように改行も可能。
カンマの付け忘れに注意 (この場合dataの後ろ)


データをnumpy配列で渡す


リスト同様。

# numpyで配列生成(1以上~6未満。5個できる)
numbers_np = np.arange(1,6)

# インデックス
index=["Aくん","Bくん","Cくん","Dくん","Eくん"]

# Seriesクラスにnumbers_npを代入
series = pd.Series(
    numbers_np, 
    index
)

print("<numpy配列>")
print(numbers_np)
print()
print("<series>")
print(series)
<numpy配列>
[1 2 3 4 5]

<series>
Aくん    1
Bくん    2
Cくん    3
Dくん    4
Eくん    5
dtype: int32



「データは1次元でなければならない」


一次元のSeriesクラスに多次元配列のデータを渡すと
Exception: Data must be 1-dimensional
のようなエラーが出ます。

上のコードでいくと、
numbers_np = np.arange(1,6)を、たとえばnumbers_np = np.arange(1,6).reshape(-1,1)など、
5行1列(5,1)の2次元に書き換えて実行したりするとエラーになる。



DataFrameクラスの生成


DataFrame()を使うと二次元のデータを生成します。行と列で2次元。

df_test = pd.DataFrame([
    [10,20,30],
    [40,50,60],
    [70,80,90]
])

df_test
0 1 2
0 10 20 30
1 40 50 60
2 70 80 90

DataFrame()クラスに、リストが3つ入ったリストを渡しました。
内部のリストがそれぞれ1つの行として表示されています。

  • 列の一番左の「0,1,2」はindexで行番号
  • 行の一番上の「0,1,2」はcolumnsで列番号

を示していて、指定しなければそれぞれ自動で表示されます。
※ Seriesの時は1次元なのでcolumnsの表示がありません。

<注意>
Seriesの「大文字 S」同様、DataFrame「D」と「F」は大文字。
どちらか1つでも小文字だと次のようなerror。
AttributeError: module 'pandas' has no attribute 'Dataframe' ⇐ Fを小文字で書いた


shapeで形状確認


numpyと同じく、そして上のSeriesでも使ったshapeで何行何列のデータか確認できる。

df_test.shape
(3, 3)

ndimで次元数を確認


これもnumpy同様、そして上のSeriesでも書いたように次元数が調べられる。

df_test.ndim
2



全要素数の確認


この場合、3行3列なので、3×3=9個になる。

df_test.size
9



2次元より大きな次元の配列をDataFrameに渡すとどうなる?


Excelの表や行列は「縦×横」の形なので2次元なんだろうと分かりますが、3次元以上のデータをDataFrameに渡すとERRORになります。
でも、3次元以上の配列って何でしょう? 3次元目は高さの次元? 4次元以上は? Excelシートの数みたいなもんか?
何だかよくわかりませんが、とりあえずここでは無視して、やり方だけ確認しておきます。



まずは、Numpyで3次元の配列をreshapeで生成します。

# 3行3列の2次元配列をNumpyで2つ生成する (要素数 18)
array_3d = np.arange(18).reshape(2,3,3)

print(array_3d)
print("\n配列の次元数 : ", array_3d.ndim)
[[[ 0  1  2]
  [ 3  4  5]
  [ 6  7  8]]

 [[ 9 10 11]
  [12 13 14]
  [15 16 17]]]

配列の次元数 :  3

3行3列が2つでき、次元数3となっています。
これをDataFrameクラスに渡してみますと

pd.DataFrame(array_3d)

上の実行出力は省略しますが、ValueError: Must pass 2-d inputERRORが出ます。
array_4d = np.arange(24).reshape(2,3,2,2)など、4次元とかにしても同様にエラーが出ます。

「DataFrameには2次元データを渡さなければなりません」



逆に今度はDataFrameに1次元を渡すと?


DataFrameに3次元以上のデータは渡せませんでしたが、1次元を渡すとどうなってしまうのか。

# リスト(1次元)
data_lst = ["a","b","c"]

# DataFrame
df1 = pd.DataFrame(data_lst)

# データの中身表示
print("DataFrameの中身")
print(df1)

print()
# データの形状他表示
print("DataFrameの型 : ",type(df1))
print("DataFrameの形状 : ",df1.shape)
print("DataFrameの次元数 : ",df1.ndim)
DataFrameの中身
   0
0  a
1  b
2  c

DataFrameの型 :  <class 'pandas.core.frame.DataFrame'>
DataFrameの形状 :  (3, 1)
DataFrameの次元数 :  2

indexが0~2、columnsが0で、3行1列、2次元のDataFrame型です。
DataFrameに1次元のデータを渡しても、あくまでも2次元のデータになる。
Seriesデータを列や行に追加したりする時に次元数や型に注意が必要です。これはあとで扱います。



indexとcolumnsを指定


無指定だと自動で「0,1,2・・・」とつくけど味気ないので、独自で用意してみる。

# numpyで、0~100で3行3列のint型乱数をNumpy配列で生成
np_data = np.random.randint(0,101,9).reshape(3,3)

# インデックス
index = ["呂布","張飛","趙雲"]

# 項目
columns = ["剣","槍","弓"]

# データフレーム作成
df2 = pd.DataFrame(
    np_data,
    index,
    columns
)

df2
呂布 6 40 100
張飛 67 51 10
趙雲 23 35 92

※ 数値はランダムです。

行と列に名前をつけただけで、なんか雰囲気が出てきますた。

indexとcolumnsの書き位置について


上のデータフレームを作成する時、indexとcolumnsを書く位置を入れ替えて実行するとどうなるか?

# データフレーム作成 (indexとcolumnsの書く位置を入れ替える)
df3 = pd.DataFrame(
    np_data,
    columns,
    index
)

df3
呂布 張飛 趙雲
6 40 100
67 51 10
23 35 92

書く位置を変えただけで、行名と項目名が入れ替わってしまいました。

DataFrame()の引数の順番が決まっている為です。
書く順番が変わっても、次のようにちゃんと指定して書けば大丈夫。

# データフレーム作成 
df4 = pd.DataFrame(
    np_data,
    columns = columns,
    index = index
)


df4
呂布 6 40 100
張飛 67 51 10
趙雲 23 35 92

ちゃんと狙い通りに戻った。



head()でデータの上から5行のみを見る


head()メソッドを使うと、たくさんあるデータの上から5行だけを取り出して表示できます。
どんなデータが入っているのかの確認に使ったりします。
head()はSeries、DataFrameの両方で使用できます。



データが少ないので増やしてからやりますね。

# インデックス名
index = ["呂布","張飛","趙雲","劉備","諸葛亮","関羽","曹操","孫堅","董卓","袁紹","夏候惇","周瑜","陳宮","張遼","何進"]

# 項目名
columns = ["剣","槍","弓","馬","統率","知力"]

# numpyをつかい、0以上1未満でfloat型乱数生成。rand(行数m,列数n)でm行n列の行列が生成。
np_data = np.random.rand(len(index), len(columns))

# 代入。変数dfに格納
df = pd.DataFrame(
    np_data,
    index = index,
    columns = columns
)

# 上5行だけ表示
df.head()
統率 知力
呂布 0.401721 0.417002 0.995960 0.001314 0.423581 0.343925
張飛 0.402860 0.779042 0.138389 0.475487 0.060286 0.201831
趙雲 0.507108 0.592027 0.312652 0.896567 0.607985 0.172778
劉備 0.170911 0.547296 0.610188 0.263836 0.506830 0.118035
諸葛亮 0.794512 0.523816 0.926814 0.507671 0.265099 0.354000


tail()でデータの下5行だけ見る


head()をtail()に変えれば下から5行だけ表示。
こちらもSeries、DataFrameの両方で使用できます。

# 下5行だけ表示
df.tail()
統率 知力
夏候惇 0.484538 0.925033 0.068624 0.290837 0.396926 0.224444
周瑜 0.476003 0.506794 0.321823 0.888588 0.651754 0.272417
陳宮 0.847366 0.131298 0.178125 0.253371 0.681193 0.938650
張遼 0.628514 0.934995 0.785382 0.119538 0.104330 0.044214
何進 0.521289 0.245135 0.870648 0.113655 0.791690 0.645424



head()とhead、tail()とtailの表示の違い


()をつけずdf.headdf.tailでも実行できるが、表示が変わる。
()を付けない場合、表示がズレ、1行おきの色分けもされません。
ちなみに、ターミナルからIpythonでDataFrameを表示したような場合でも、行ごとの色分けがされません。
実行表示省略します。



データの表示が省略される行数・列数


データが多い場合は、表で一部のデータが表示されなくなり省略されます。

Series、DataFrameともに、データの形状が

  • 行 : 60行以下 (Seriesはこちら)
  • 列 : 20列以下

の場合は、全てのデータを表示。


それを超えると、つまりSeriesは(61,)、DataFrameは(61,21)のshapeの場合は

  • 行 : 上下各5行 (Seriesはこちら)
  • 列 : 左右各10列

は表示して、中間は「・・・」と省略された。
全ての環境でそうなるのか、設定できるのか、などは調べてません。
とりあえずスマホでやると、何行何列であろうと非常に見難い(笑)・・・。



loc 必要な値だけを取り出す


「SeriesやDataFrameのデータから、特定の値、特定行や特定の列だけ取り出したい」
というような時、locを使うとできます。
locに似たilocという物がありますが、後でやります。
locを使うときはloc[行名, 列名]のように具体的なindex名columns名を指定します。



上で作ったSeriesとDataFrameを使いまわして確認します。

Seriesの場合


とりあえず上で作ったSeriesデータの表示。

# 上で作ったSeriesの確認
series
Aくん    1
Bくん    2
Cくん    3
Dくん    4
Eくん    5
dtype: int32



locでSeriesデータの「値のみ」を抽出


「Cくん」のデータだけ取り出してみる。
「3」が返ってくればOK。

# loc[index名]で値を取り出す
series.loc["Cくん"]
3

実は、locをつけなくとも取り出せる。

series["Cくん"]
3



locでindex名と値を同時に抽出


カッコの中をリストにすると

series.loc[["Aくん"]]
Aくん    0
dtype: int32



locで複数のindexと値を抽出


AくんとEくんを取り出してみよう。リストで複数指定する。

series.loc[["Aくん","Eくん"]]
Aくん    0
Eくん    4
dtype: int32

locをつけずとも同様。

series[["Aくん","Eくん"]]
Aくん    0
Eくん    4
dtype: int32



locで範囲を指定し抽出


C~Eくんを抽出する。スライスを使う
<注意>
スライスの、指定した後ろの値も含まれる。

series.loc["Cくん":"Eくん"]
Cくん    2
Dくん    3
Eくん    4
dtype: int32

locを外しても同様に↓。

series["Cくん":"Eくん"]
Cくん    2
Dくん    3
Eくん    4
dtype: int32



DataFrameの場合


DataFrameの場合は、loc[ 行範囲 , 列範囲 ] とすると指定の行と列を取り出せる。
列範囲を省略し行のみを指定すると、指定行を全列抽出する。



DataFrameデータの確認


こちらも上で作ったものを使いまわします。



locでDataFrameの特定行を抽出


indexだけ指定すると(columnsの指定を省略すると)、その行のみを全列抽出する。
諸葛亮の行を取り出してみる。

df.loc["諸葛亮"]
剣     0.794512
槍     0.523816
弓     0.926814
馬     0.507671
統率    0.265099
知力    0.354000
Name: 諸葛亮, dtype: float64



DataFrameの場合、locを外して実行したら、ERRORになりました。
SeriesもDataFrameも、ちゃんとlocをつけた方がいいですね。



locで複数の指定行を抽出


曹操と夏候惇と呂布を取り出してみます。

df.loc[["曹操","夏候惇","呂布"]]
統率 知力
曹操 0.980313 0.481871 0.237070 0.216141 0.630027 0.194746
夏候惇 0.484538 0.925033 0.068624 0.290837 0.396926 0.224444
呂布 0.401721 0.417002 0.995960 0.001314 0.423581 0.343925

これも列の指定を省略しているので、全列抽出された。



locで指定行の指定列を抽出


列を取り出す場合は、loc[行指定, 列指定] とすると、指定の行の列を抽出できる。

たとえば、

  • 全ての行の
  • 「槍」「統率」の列だけ

を取り出したいなら、

  • 行 : スライスで全行「:」指定
  • 列 : リストで複数指定

のようにする。

df.loc[ : , ["槍","統率"]]
統率
呂布 0.417002 0.423581
張飛 0.779042 0.060286
趙雲 0.592027 0.607985
劉備 0.547296 0.506830
諸葛亮 0.523816 0.265099
関羽 0.889468 0.905001
曹操 0.481871 0.630027
孫堅 0.869599 0.732994
董卓 0.464023 0.099116
袁紹 0.050154 0.853701
夏候惇 0.925033 0.396926
周瑜 0.506794 0.651754
陳宮 0.131298 0.681193
張遼 0.934995 0.104330
何進 0.245135 0.791690



  • 「スライスで範囲指定」
  • 「リストで個別に複数を指定」

で使い分けすれば狙ったものが自在に取り出せる。



iloc 数字指定で行抽出


上で見てきたように、locは具体的な名前で行や列を指定して抽出しましたが、ilocは整数でindexやcolumnsを指定し抽出します。



iloc Seriesから値を抽出


# データの表示確認
series
Aくん    1
Bくん    2
Cくん    3
Dくん    4
Eくん    5
dtype: int32

Aくんから順に、index番号は0,1,2・・・です。通常のリストやタプルなどと同じ。

# 最終行指定で抽出するなら
series.iloc[-1] # 5
5
# リストでindex指定してindex名も表示
series.iloc[[-1]] # index名と値を出力
Eくん    5
dtype: int32
# 複数indexをリストで指定
# 1と3、即ちBとDを抽出
series.iloc[[1,3]] # B:2 , D:4
Bくん    2
Dくん    4
dtype: int32



iloc Seriesからスライスで抽出


[何以上:何未満]でスライス。
<注意>
指定した後ろの値は含まれない

# indexの2~4、即ちC~Dくんを抽出
series.iloc[2:4] 
Cくん    2
Dくん    3
dtype: int32



iloc DataFrameから抽出


上で作ったDataFrameをまたまた使い回します。変数dfの変な三国志のやつ。

iloc 行指定抽出


パッと見て、誰が何番のindexかが分かりませんね・・・。
ilocはindex名を付けずに自動で割り振ったような場合に使うのがよさげです。

とはいえ、孫堅を取り出します。0,1,2,と数えて行ったところ上から8番目なので、indexは7。

df.iloc[7]
剣     0.177267
槍     0.869599
弓     0.408910
馬     0.967722
統率    0.732994
知力    0.564545
Name: 孫堅, dtype: float64



index番号を取得するindex.get_loc()


ぐぬぬ...このままでは埒があかぬ。
index.get_loc(インデックス名)を使えばindex番号が取得できるようじゃ。
袁紹は何番かな?

# データ
df
統率 知力
呂布 0.401721 0.417002 0.995960 0.001314 0.423581 0.343925
張飛 0.402860 0.779042 0.138389 0.475487 0.060286 0.201831
趙雲 0.507108 0.592027 0.312652 0.896567 0.607985 0.172778
劉備 0.170911 0.547296 0.610188 0.263836 0.506830 0.118035
諸葛亮 0.794512 0.523816 0.926814 0.507671 0.265099 0.354000
関羽 0.776844 0.889468 0.773801 0.381681 0.905001 0.837660
曹操 0.980313 0.481871 0.237070 0.216141 0.630027 0.194746
孫堅 0.177267 0.869599 0.408910 0.967722 0.732994 0.564545
董卓 0.229813 0.464023 0.239242 0.232900 0.099116 0.032595
袁紹 0.810562 0.050154 0.418373 0.310994 0.853701 0.788780
夏候惇 0.484538 0.925033 0.068624 0.290837 0.396926 0.224444
周瑜 0.476003 0.506794 0.321823 0.888588 0.651754 0.272417
陳宮 0.847366 0.131298 0.178125 0.253371 0.681193 0.938650
張遼 0.628514 0.934995 0.785382 0.119538 0.104330 0.044214
何進 0.521289 0.245135 0.870648 0.113655 0.791690 0.645424
# index番号を取り出す
df.index.get_loc("袁紹")
9



iloc DataFrameから複数の行指定で抽出


関羽張遼何進をilocで取り出す。
だが、index番号が分からないし数えるわけにもいかないので、上で使ったindex.get_loc()を使います。

# index番号を取得
id_1 = df.index.get_loc("関羽")
id_2 = df.index.get_loc("張遼")
id_3 = df.index.get_loc("何進")

# リストで行指定の全列抽出
df.iloc[[id_1, id_2, id_3]]
統率 知力
関羽 0.776844 0.889468 0.773801 0.381681 0.905001 0.837660
張遼 0.628514 0.934995 0.785382 0.119538 0.104330 0.044214
何進 0.521289 0.245135 0.870648 0.113655 0.791690 0.645424



iloc DataFrameから範囲の行と列を抽出


孫堅周瑜の行で、列は統率以降全部を取り出してみる。
ですが、ilocはスライスの後ろ側で指定した番号を含まないので、指定の際に+1します。

列番号を調べるにはdf.columns.get_loc("列名")とすればいいようです。
上で使ったindex.get_loc("行名")indexと行名columnsと列名 に変えただけ。

# index取得
id_min = df.index.get_loc("孫堅")
id_max = df.index.get_loc("周瑜") 
# columns取得
col_min = df.columns.get_loc("統率")

df.iloc[ id_min : id_max+1 , col_min : ]
統率 知力
孫堅 0.732994 0.564545
董卓 0.099116 0.032595
袁紹 0.853701 0.788780
夏候惇 0.396926 0.224444
周瑜 0.651754 0.272417



抽出したデータを別のDataFrameとして再利用するには


これまでlocやilocを使って、元々のデータから一部を抽出して来ました。
この方法は、抽出してるだけで元データは上書きされるような事もなくそのまま残こっていますので安心です。

取り出したデータだけを再利用したい場合は
df_ryuubi = df.loc["劉備"]
のように別の適当な変数に格納してやれば、抽出したDataFrameがその変数に格納されます。(Seriesも同様)



DataFrameに個数のバラバラな配列を渡すと欠損値に


ところで、要素数がまちまちの複数のリストをDataFrameクラスにリストで渡すとどうなるでしょうか。

# リスト(個数がバラバラ)
lst_1 = [1,2,3]
lst_2 = [10,20,30,40,50]
lst_3 = [100,200]


df_vari = pd.DataFrame([lst_1, lst_2, lst_3])
df_vari
0 1 2 3 4
0 1 2 3.0 NaN NaN
1 10 20 30.0 40.0 50.0
2 100 200 NaN NaN NaN

ERRORは出ない。
個数最大のリストの行に合わせて不足分はNaNで欠損値として表示。
2列目以降は小数点が付いています。



SeriesをDataFrameに変換するには?


Numpyのreshape(行,列)が使えるかな?と試したが、AttributeError: 'Series' object has no attribute 'reshape'のERRORが出る。
Pandasにreshapeは使えないようです。
DataFrame()にSeriesをそのまま渡すと2次元に変換されたDataFrameができる。

# Series生成
s1 = pd.Series([1,2,3,4,5,6])

# DataFrameクラスに渡して変換
df_s1 = pd.DataFrame(s1)

# 形状と次元の確認
print("元のSeriesデータ s1 : 形状:{} 次元:{}".format(s1.shape, s1.ndim))
print("DataFrameに渡した後 df_s1 : 形状:{} 次元:{}".format(df_s1.shape, df_s1.ndim))
元のSeriesデータ s1 : 形状:(6,) 次元:1
DataFrameに渡した後 df_s1 : 形状:(6, 1) 次元:2



一応SeriesとDataFrameをそれぞれ表示させておきます。
後者で2次元になったので、一番上にcolumnsが0と付き、1行おきに色分けもされます。

# 前(Series型)
s1
0    1
1    2
2    3
3    4
4    5
5    6
dtype: int64
# 後(DataFrame型)
df_s1
0
0 1
1 2
2 3
3 4
4 5
5 6



DataFrameをSeriesに変換するには?


こんなことをする状況があるのか知らないが、一応。
DataFrameは2次元でSeriesは1次元なので、SeriesにするにはDataFrameを1次元配列の形に変形しないといけません。

Numpyで多次元を1次元に変形するにはravel()を使うとできますが、Pandasでravel()は使えないようなので、DataFrameを 一旦Numpy配列に変換してから1次元に変形します。

PandasのDataFrameからNumpyのNdarrayに変換


valuesを使うとNumpy配列に変換されます。
また変な三国志のやつを使い回します。

# DataFrameをNdarrayに変換して変数に格納
narray_df = df.values
# 表示
narray_df
array([[0.40172103, 0.41700196, 0.99596008, 0.00131395, 0.4235807 ,
        0.34392501],
       [0.40285983, 0.77904236, 0.13838936, 0.4754866 , 0.06028554,
        0.20183112],
       [0.50710816, 0.59202655, 0.31265243, 0.89656746, 0.60798491,
        0.17277816],
       [0.17091077, 0.54729648, 0.6101883 , 0.26383571, 0.50682996,
        0.11803534],
       [0.79451234, 0.52381641, 0.92681373, 0.50767126, 0.26509927,
        0.35400032],
       [0.77684376, 0.88946831, 0.77380134, 0.38168061, 0.90500101,
        0.83766001],
       [0.98031303, 0.4818708 , 0.23706966, 0.21614067, 0.63002656,
        0.19474565],
       [0.17726671, 0.86959902, 0.40890954, 0.96772171, 0.73299389,
        0.56454476],
       [0.22981335, 0.46402294, 0.23924217, 0.23290045, 0.09911601,
        0.03259544],
       [0.81056219, 0.05015428, 0.41837329, 0.31099448, 0.85370138,
        0.78877963],
       [0.48453787, 0.92503338, 0.06862379, 0.29083687, 0.39692594,
        0.22444407],
       [0.4760027 , 0.5067937 , 0.32182294, 0.88858763, 0.6517536 ,
        0.27241705],
       [0.84736616, 0.13129806, 0.17812463, 0.25337085, 0.68119349,
        0.93865021],
       [0.62851363, 0.93499539, 0.78538165, 0.11953763, 0.10433006,
        0.04421394],
       [0.52128914, 0.24513533, 0.87064805, 0.11365535, 0.7916898 ,
        0.64542413]])

変な三国志のindex名とcolumns名が消えて、数値だけのデータになりました。
一応、形状と次元と型を確認しておきます。

print(narray_df.shape)
print(narray_df.ndim)
print(type(narray_df))
(15, 6)
2
<class 'numpy.ndarray'>

15行6列で2次元のNumpy配列ndarrayに変換されています。

これを更に1次元に変形して、PandasのSeriesクラスに渡します。
Numpyで配列を1次元に変形するにはravel()を使うとできます。

# Numpy配列を、1次元のNumpy配列に変換
new_1d_array = narray_df.ravel()

# 形状と次元と型
print(new_1d_array.shape)
print(new_1d_array.ndim)
print(type(new_1d_array))
(90,)
1
<class 'numpy.ndarray'>

90行、1次元、Numpy配列に変換されましたので、これをPandas.Series()に代入すればSeries型のデータに変換完了。

# Seriesに1次元Numpy配列を代入
new_series = pd.Series(new_1d_array)

# 形状と次元と型
print(new_series.shape)
print(new_series.ndim)
print(type(new_series))
(90,)
1
<class 'pandas.core.series.Series'>

これで15行6列のDataFrameからSeriesに変換することができました。



長いので一旦ここで切ります。
つづきはこちら【Python機械学習】pandasの基本的な使い方2