Numpyの0d配列はなぜスカラーとみなされないのですか?
質問
確かに0d配列はスカラーですが、Numpyはそう考えていないようです。何か見落としているのか、それとも私がその概念を誤解しているだけなのでしょうか?
>>> foo = numpy.array(1.11111111111, numpy.float64)
>>> numpy.ndim(foo)
0
>>> numpy.isscalar(foo)
False
>>> foo.item()
1.11111111111
どのように解決するのですか?
あまり難しく考えない方がいい。その方が結局は個人の精神衛生上も寿命的にも良いのです。
Numpyのスカラー型に関する不思議な状況は、1x1行列をスカラー型に劣化させる優雅で一貫した方法がないという事実から産み出されました。数学的には同じものであるにもかかわらず、これらは非常に異なるコードによって処理されます。
もしあなたが科学的なコードを少しでも書いていたなら、最終的には以下のようなものを望むでしょう。
max(a)
のようなものが、スカラーであっても、すべてのサイズの行列で動作することを望むでしょう。数学的には、これは完全に理にかなったことです。しかし、プログラマにとっては、Numpy でスカラーを示すものはすべて .shape と .ndim 属性を持つべきであり、少なくとも ufuncs は Numpy の 21 種類のスカラーに対して入力で明示的に型チェックを行う必要がないことを意味しているのです。
一方、既存のPythonのライブラリで は で明示的に型チェックを行う既存のPythonライブラリとも連携する必要があります。これはジレンマで、Numpyのndarrayはスカラーになったときに個別に型を変更しなければならず、すべてのアクセスに対してチェックを行わないと、それが発生したかどうか知る方法がありません。実際にそのルートを進むと、スカラー型の基準では、おそらくビット動作がとんでもなく遅くなってしまうでしょう。
Numpy開発者の解決策は、独自のスカラー型のためにndarrayとPythonのスカラーの両方を継承し、すべてのスカラーが.shape、.ndim、.T、などなどを持っているようにすることです。1x1 の行列はまだ存在しますが、スカラーを扱うことが分かっている場合は、その使用は控えるようにします。これは理論的にはうまくいくはずですが、時折、ペイント ローラーで失敗した場所を目にすることがあり、醜い内部がすべての人に見えるように露出していることがあります。
>>> from numpy import *
>>> a = array(1)
>>> b = int_(1)
>>> a.ndim
0
>>> b.ndim
0
>>> a[...]
array(1)
>>> a[()]
1
>>> b[...]
array(1)
>>> b[()]
1
特に理由はないのですが
a[...]
と
a[()]
は異なるものを返すべきですが、そうなっています。これを変更するための提案がありますが、1x1 配列のための仕事を終えるのを忘れていたようです。
潜在的により大きな、そしておそらく解決不可能な問題は、Numpyのスカラーがイミュータブルであるという事実です。したがって、スカラーを ndarray に噴霧すること、数学的には配列をスカラーに折り畳むことの隣接操作は、実装するのが困難です。Numpyのスカラーを実際に成長させることはできませんし、定義上ndarrayにキャストすることはできませんが、たとえ
newaxis
は不思議と機能するのですが。
>>> b[0,1,2,3] = 1
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: 'numpy.int32' object does not support item assignment
>>> b[newaxis]
array([1])
Matlabでは、スカラーのサイズを大きくすることは全く問題なく、頭を使わない操作です。Numpyの場合は、ジャラジャラしたものをくっつける必要があります。
a = array(a)
を貼り付けなければならない。
を考える
で、スカラーで始まって配列で終わる可能性があります。私はNumpyがPythonとうまくやるためにこのようにしなければならない理由を理解していますが、だからといって、多くの新しいスイッチャーがこのことに深く戸惑っているという事実は変わりません。この挙動に苦労して、最終的に我慢した明確な記憶を持っている人もいれば、あまりに行き過ぎた人は、大抵、最も純真な夢に頻繁につきまとう、深い形のない心の傷が残っています。それは、すべての人にとって醜い状況です。
関連
-
[解決済み] argparseによるブーリアン値のパース
-
[解決済み] UnicodeEncodeError: 'ascii' codec can't encode character u'\xa0' in position 20: ordinal not in range(128)
-
[解決済み] なぜC++はPythonよりもstdinからの行の読み込みが遅いのですか?
-
[解決済み] 複数行の長い文字列を作成するためのPythonicな方法
-
[解決済み] mixinとは何か、なぜ有用なのか?
-
[解決済み】Ellipsisオブジェクトは何をするのですか?
-
[解決済み】PILイメージをnumpyの配列に変換する方法は?
-
[解決済み] SQLAlchemy: 日付フィールドをフィルタリングする方法は?
-
[解決済み] データフレームをソートした後にインデックスを更新する
-
[解決済み] Python Logging でログメッセージが2回表示される件
最新
-
nginxです。[emerg] 0.0.0.0:80 への bind() に失敗しました (98: アドレスは既に使用中です)
-
htmlページでギリシャ文字を使うには
-
ピュアhtml+cssでの要素読み込み効果
-
純粋なhtml + cssで五輪を実現するサンプルコード
-
ナビゲーションバー・ドロップダウンメニューのHTML+CSSサンプルコード
-
タイピング効果を実現するピュアhtml+css
-
htmlの選択ボックスのプレースホルダー作成に関する質問
-
html css3 伸縮しない 画像表示効果
-
トップナビゲーションバーメニュー作成用HTML+CSS
-
html+css 実装 サイバーパンク風ボタン
おすすめ
-
[解決済み] NumPy, RuntimeWarning: 電源で無効な値が発生しました。
-
[解決済み] DataFrameの文字列、dtypeがobjectの場合
-
[解決済み] PythonでファイルのMD5チェックサムを計算するには?重複
-
[解決済み] pandasのDataFrameから空のセルを含む行を削除する
-
[解決済み] googletransがエラー 'NoneType' オブジェクトに 'group' 属性がない、と言って動かなくなった。
-
[解決済み] Pythonのインスタンス変数とクラス変数
-
[解決済み] python-requests モジュールからのすべてのリクエストをログに記録します。
-
[解決済み] オブジェクトのリストに特定の属性値を持つオブジェクトが含まれているかどうかをチェックする
-
[解決済み] Ctrl-CでPythonスクリプトを終了できない
-
[解決済み] Jupyter (IPython)ノートブックのセッションをpickleして保存する方法