NumPy 1.15.0 發行說明#

NumPy 1.15.0 版本進行了異常大量的清理工作、許多舊函數的棄用,以及對許多現有函數的改進。請閱讀以下詳細說明,以查看您是否受到影響。

在測試方面,我們已切換到 pytest 作為不再維護的 nose 框架的替代品。舊的基於 nose 的介面仍然保留,以供可能仍在使用它的下游專案使用。

此版本支援的 Python 版本為 2.7、3.4-3.7。這些 wheels 連結了 OpenBLAS v0.3.0,這應該可以解決 NumPy 1.14 報告的一些線性代數問題。

重點#

  • NumPy 已切換到 pytest 進行測試。

  • 新的 numpy.printoptions 內容管理器。

  • 直方圖函數的許多改進。

  • 在 python 2.7 中支援 unicode 欄位名稱。

  • 改進了對 PyPy 的支援。

  • 修復和改進了 numpy.einsum

新函數#

  • numpy.gcdnumpy.lcm,用於計算最大公約數和最小公倍數。

  • numpy.ma.stacknumpy.stack 陣列連接函數推廣到遮罩陣列。

  • numpy.quantile 函數,一個沒有 100 因子的 percentile 介面

  • numpy.nanquantile 函數,一個沒有 100 因子的 nanpercentile 介面

  • numpy.printoptions,一個內容管理器,可在 with 區塊的範圍內暫時設定列印選項

    >>> with np.printoptions(precision=2):
    ...     print(np.array([2.0]) / 3)
    [0.67]
    
  • numpy.histogram_bin_edges,一個用於取得直方圖使用的 bin 邊緣的函數,而無需計算直方圖。

  • C 函數 npy_get_floatstatus_barriernpy_clear_floatstatus_barrier 已新增,以處理編譯器最佳化變更運算順序的問題。詳情請見下文。

棄用#

  • 內建 pickle 函數的別名已被棄用,建議使用未別名的 pickle.<func> 名稱

    • numpy.loads

    • numpy.core.numeric.load

    • numpy.core.numeric.loads

    • numpy.ma.loads, numpy.ma.dumps

    • numpy.ma.load, numpy.ma.dump - 這些函數在 python 3 上使用字串呼叫時已經失敗。

  • 除了元組之外,任何其他形式的多維索引皆已棄用。這表示 ind = [slice(None), 0]; arr[ind] 中的索引列表應變更為元組,例如,ind = [slice(None), 0]; arr[tuple(ind)]arr[(slice(None), 0)]。此變更對於避免諸如 arr[[[0, 1], [0, 1]]] 之類的表達式中的歧義是必要的,目前該表達式被解釋為 arr[array([0, 1]), array([0, 1])],未來將被解釋為 arr[array([[0, 1], [0, 1]])]

  • 以下子模組的匯入已被棄用,它們將在未來的某個日期移除。

    • numpy.testing.utils

    • numpy.testing.decorators

    • numpy.testing.nosetester

    • numpy.testing.noseclasses

    • numpy.core.umath_tests

  • 現在不建議將產生器提供給 numpy.sum。這是未記錄的行為,但有效。先前,它會計算產生器表達式的總和。未來,它可能會傳回不同的結果。請改用 np.sum(np.from_iter(generator)) 或內建 Python sum

  • C-API 的使用者應在解除分配陣列之前,對任何設定了 WRITEBACKIFCOPY 旗標的陣列呼叫 PyArrayResolveWriteBackIfCopyPyArray_DiscardWritebackIfCopy。如果需要時未使用這些呼叫,將發出棄用警告。

  • nditer 的使用者應在任何迭代器運算元可寫入時,將 nditer 物件用作內容管理器,以便 numpy 可以管理回寫語意,或者應呼叫 it.close()。否則,在這些情況下可能會發出 RuntimeWarning

  • np.histogramnormed 引數在 1.6.0 版本中早已棄用,現在會發出 DeprecationWarning

未來變更#

  • NumPy 1.16 將停止支援 Python 3.4。

  • NumPy 1.17 將停止支援 Python 2.7。

相容性注意事項#

編譯後的測試模組已重新命名並設為私有#

以下編譯後的模組已重新命名並設為私有

  • umath_tests -> _umath_tests

  • test_rational -> _rational_tests

  • multiarray_tests -> _multiarray_tests

  • struct_ufunc_test -> _struct_ufunc_tests

  • operand_flag_tests -> _operand_flag_tests

umath_tests 模組仍然可用於向後相容性,但未來將會移除。

np.savez 傳回的 NpzFile 現在是 collections.abc.Mapping#

這表示它的行為類似唯讀字典,並且具有新的 .values() 方法和 len() 實作。

對於 python 3,這表示 .iteritems().iterkeys() 已被棄用,而 .keys().items() 現在傳回視圖而不是列表。這與內建 dict 類型在 python 2 和 python 3 之間變更的方式一致。

在某些條件下,nditer 必須在內容管理器中使用#

當使用帶有 "writeonly""readwrite" 旗標的 numpy.nditer 時,在某些情況下,nditer 實際上不會為您提供可寫入陣列的視圖。相反,它會為您提供副本,如果您對副本進行變更,nditer 後來會將這些變更寫回您的實際陣列。目前,此回寫發生在陣列物件被垃圾回收時,這使得此 API 在 CPython 上容易出錯,並且在 PyPy 上完全損壞。因此,每當 nditer 與可寫入陣列一起使用時,現在都應將其用作內容管理器,例如,with np.nditer(...) as it: ...。您也可以針對無法使用內容管理器的情況(例如,在產生器表達式中)明確呼叫 it.close()

Numpy 已切換為使用 pytest 而不是 nose 進行測試#

最後一個 nose 版本是 2015 年 6 月的 1.3.7,並且該工具的開發已結束,因此 NumPy 現在已切換為使用 pytest。先前某些下游專案使用的舊裝飾器和 nose 工具仍然可用,但不會維護。標準測試實用程式 assert_almost_equal 等不受此變更的影響,但 nose 特定的函數 import_noseraises 除外。這些函數在 numpy 中未使用,但為了向下相容性而保留。

Numpy 不再使用 __array_interface__ monkey-patch ctypes#

先前 numpy 將 __array_interface__ 屬性新增到 ctypes 中的所有整數類型。

np.ma.notmasked_contiguousnp.ma.flatnotmasked_contiguous 始終傳回列表#

這是已記錄的行為,但先前結果可能是 slice、None 或 list 中的任何一個。

所有下游使用者似乎都檢查來自 flatnotmasked_contiguousNone 結果,並將其替換為 []。這些呼叫者將繼續像以前一樣工作。

np.squeeze 還原了無法處理 axis 引數的物件的舊行為#

在版本 1.7.0 之前,numpy.squeeze 沒有 axis 引數,並且預設情況下會移除所有空軸。合併 axis 引數使得可以有選擇地擠壓單個或多個空軸,但由於軸仍然可以從期望移除所有空軸的物件中選擇性地移除(靜默成功),因此舊的 API 期望未得到尊重。對於期望舊行為的物件,靜默、選擇性地移除空軸的問題已得到修復,並且舊行為已還原。

非結構化 void 陣列的 .item 方法現在傳回 bytes 物件#

.item 現在傳回 bytes 物件而不是緩衝區或位元組陣列。這可能會影響假定傳回值是可變的程式碼,但現在情況已非如此。

copy.copycopy.deepcopy 不再將 masked 轉換為陣列#

由於 np.ma.masked 是唯讀純量,因此複製應該是無操作。這些函數現在的行為與 np.copy() 一致。

結構化陣列的多欄位索引仍然會傳回副本#

結構化陣列的多欄位索引傳回視圖而不是副本的變更已推遲到 1.16 版本。已引入新的方法 numpy.lib.recfunctions.repack_fields,以協助減輕此變更的影響,該方法可用於編寫與 numpy 1.15 和 1.16 相容的程式碼。有關如何更新程式碼以適應此未來變更的更多資訊,請參閱使用者指南的「存取多個欄位」章節。

C API 變更#

新函數 npy_get_floatstatus_barriernpy_clear_floatstatus_barrier#

已新增函數 npy_get_floatstatus_barriernpy_clear_floatstatus_barrier,應取代 npy_get_floatstatus``and ``npy_clear_status 函數使用。當在 ufunc SIMD 函數中使用先前的函數時,GCC 8.1 和 Clang 等最佳化編譯器會重新排列運算順序,導致在我們想要檢查其狀態的運算執行之前檢查 floatstatus 旗標。請參閱 #10339

PyArray_GetDTypeTransferFunction 的變更#

PyArray_GetDTypeTransferFunction 現在預設為對使用者定義的 dtype 使用使用者定義的 copyswapn / copyswap。如果這導致效能顯著下降,請考慮實作 copyswapn 以反映 PyArray_GetStridedCopyFn 的實作。請參閱 #10898

新功能#

為整數和物件類型新增 np.gcdnp.lcm ufuncs#

這些分別計算最大公約數和最小公倍數。這些適用於所有 numpy 整數類型,以及內建的任意精度 Decimallong 類型。

支援 iOS 的跨平台建置#

已修改建置系統以新增對 _PYTHON_HOST_PLATFORM 環境變數的支援,該變數由 distutils 在一個平台上為另一個平台編譯時使用。這使得可以為 iOS 目標編譯 NumPy。

這僅允許您一次為一個特定平台編譯 NumPy。建立完整的 iOS 相容 NumPy 套件需要為 iOS 支援的 5 種架構(i386、x86_64、armv7、armv7s 和 arm64)建置,並將這 5 個編譯後的建置產品合併為單個「fat」二進位檔案。

np.intersect1d 新增 return_indices 關鍵字#

新的關鍵字 return_indices 傳回與共同元素對應的兩個輸入陣列的索引。

np.quantilenp.nanquantile#

類似於 np.percentilenp.nanpercentile,但採用 [0, 1] 中的分位數,而不是 [0, 100] 中的百分位數。np.percentile 現在是 np.quantile 的一個精簡包裝函式,額外步驟是除以 100。

建置系統#

新增了對 64 位元 RISC-V 架構的實驗性支援。

改進#

np.einsum 更新#

同步 numpyopt_einsum 之間的 einsum 路徑最佳化技術。特別是,greedy 路徑已收到 @jcmgray 的許多增強功能。已修復問題的完整列表如下

  • 任意記憶體可以傳遞到 greedy 路徑。修復 gh-11210。

  • greedy 路徑已更新,包含更多動態規劃概念,防止大量重複(且昂貴)的呼叫,這些呼叫會找出實際發生的配對收縮。現在在數百個輸入張量上只需幾秒鐘。適用於矩陣乘積狀態理論。

  • 重新處理 gh-11218 gh-10352 中發現的廣播點錯誤捕獲,使其在流程中更早發生。

  • 增強了先前錯過邊緣案例(gh-11308 的一部分)的 can_dot 功能。

np.flip 可以跨多個軸運作#

np.flip 現在在其 axis 引數中接受 None 或整數元組。如果 axis 為 None,它將跨所有軸翻轉。

histogramhistogramdd 函數已移至 np.lib.histograms#

這些函數最初位於 np.lib.function_base 中。它們仍然在其未限定範圍的 np.histogram(dd) 名稱下可用,並且為了保持相容性,在 np.lib.function_base.histogram(dd) 中使用別名。

執行 from np.lib.function_base import * 的程式碼需要使用新位置進行更新,並且應考慮未來不要使用 import *

histogram 在給定明確的 bins 時將接受 NaN 值#

先前,當嘗試計算資料的有限範圍時,它會失敗。由於在明確給定 bins 時無論如何都會忽略範圍,因此此錯誤是不必要的。

請注意,對 NaN 值呼叫 histogram 仍然會引發使用 nan 值時典型的 RuntimeWarning,可以使用 errstate 像往常一樣使其靜音。

histogram 在給定明確的 bin 邊緣時適用於 datetime 類型#

現在可以對日期、時間和時間差進行直方圖化。必須明確傳遞 bin 邊緣,並且尚未自動計算。

histogram “auto” 估計器更好地處理有限變異數#

IQR 為 0 不再導致 n_bins=1,而是選擇的 bin 數量與這種情況下的資料大小相關。

histogram`histogramdd 傳回的邊緣現在與資料浮點類型相符#

當傳遞 np.float16np.float32np.longdouble 資料時,傳回的邊緣現在具有相同的 dtype。先前,histogram 僅在給定明確的 bins 時才會傳回相同的類型,而 histogram 無論輸入如何都會產生 float64 bins。

histogramdd 允許在軸子集中給定明確的範圍#

numpy.histogramddrange 引數現在可以包含 None 值,以指示應從資料計算對應軸的範圍。先前,這不能在每個軸的基礎上指定。

histogramddhistogram2d 的 normed 引數已重新命名#

這些引數現在稱為 density,這與 histogram 一致。舊引數繼續有效,但應優先使用新名稱。

np.r_ 適用於 0d 陣列,而 np.ma.mr_ 適用於 np.ma.masked#

傳遞給 r_mr_ 連接輔助函數的 0d 陣列現在被視為長度為 1 的陣列。先前,傳遞這些陣列會產生錯誤。因此,numpy.ma.mr_ 現在可以在 masked 常數上正確運作。

np.ptp 接受 keepdims 引數和擴展軸元組#

np.ptp (峰對峰值) 現在可以像 np.maxnp.min 一樣,跨多個軸運作。

MaskedArray.astype 現在與 ndarray.astype 完全相同#

這表示它接受所有相同的參數,使更多為 ndarray 編寫的程式碼也能用於遮罩陣列。

在編譯時啟用 AVX2/AVX512#

變更為 simd.inc.src 以允許在編譯時使用 AVX2 或 AVX512。先前,即使程式碼的其餘部分獲得 AVX2,使用 -march=native 編譯 avx2 (或 512) 仍然會對 simd 函數使用 SSE 程式碼。

nan_to_num 在接收純量或 0 維輸入時總是回傳純量#

先前,整數純量輸入會回傳陣列,這與浮點數輸入以及通用函數 (ufuncs) 的行為不一致。對於所有類型的純量或 0 維輸入,結果現在都是純量。

np.flatnonzero 可用於 numpy 可轉換的類型#

np.flatnonzero 現在使用 np.ravel(a) 而不是 a.ravel(),因此它適用於列表、元組等。

np.interp 回傳 numpy 純量而不是內建純量#

先前,np.interp(0.5, [0, 1], [10, 20]) 會回傳 float,但現在它回傳 np.float64 物件,這更符合其他函數的行為。

此外,不再支援 np.interp(object_array_0d, ...) 的特殊情況,因為 np.interp(object_array_nd) 從未被支援。

由於此變更,period 參數現在可以用於 0 維陣列。

允許 dtype 欄位名稱在 Python 2 中使用 unicode#

先前,np.dtype([(u'name', float)]) 在 Python 2 中會引發 TypeError,因為只有位元組字串允許用於欄位名稱。現在,任何 unicode 字串欄位名稱都將使用 ascii 編碼解碼器進行編碼,失敗時會引發 UnicodeEncodeError

此變更使得使用 from __future__ import unicode_literals 撰寫與 Python 2/3 相容的程式碼更容易,先前這會導致字串文字欄位名稱在 Python 2 中引發 TypeError。

比較通用函數接受 dtype=object,覆寫預設的 bool#

這允許符號類型的物件陣列 (覆寫 == 和其他運算子以回傳表達式) 可以使用 np.equal(a, b, dtype=object) 逐元素比較。

sort 函數接受 kind='stable'#

到目前為止,為了對資料執行穩定排序,使用者必須執行

>>> np.sort([5, 2, 6, 2, 1], kind='mergesort')
[1, 2, 2, 5, 6]

因為合併排序是 NumPy 中唯一可用的穩定排序演算法。然而,使用 kind=’mergesort’ 並未明確表示使用者想要執行穩定排序,因此損害了可讀性。

此變更允許使用者指定 kind=’stable’,從而闡明意圖。

對於就地累加,不要建立暫時副本#

當通用函數執行累加時,由於輸入和輸出之間的重疊,它們不再建立暫時副本,也就是說,在累加結果儲存到其位置之前,會先加入下一個累加的元素,因此重疊是安全的。避免複製可以加快執行速度。

linalg.matrix_power 現在可以處理矩陣堆疊#

linalg 中的其他函數一樣,matrix_power 現在可以處理維度大於 2 的陣列,這些陣列被視為矩陣堆疊。作為變更的一部分,為了進一步提高一致性,第一個引數的名稱已變更為 a (從 M),並且非平方矩陣的例外已變更為 LinAlgError (從 ValueError)。

random.permutation 在多維陣列中的效能提升#

permutation 對於所有輸入陣列維度,都使用 random.shuffle 中的快速路徑。先前,快速路徑僅用於一維陣列。

廣義通用函數現在接受 axesaxiskeepdims 參數#

可以透過傳入 axes 參數 (特定軸索引的元組列表) 來控制廣義通用函數在哪些軸上運作。例如,對於適用於矩陣乘法的 (i,j),(j,k)->(i,k) 簽名,基本元素是二維矩陣,並且這些矩陣被認為儲存在每個引數的最後兩個軸中。對應的 axes 關鍵字將是 [(-2, -1), (-2, -1), (-2, -1)]。如果想要改用前導維度,則會傳入 [(0, 1), (0, 1), (0, 1)]

為了簡化起見,對於在 1 維陣列 (向量) 上運作的廣義通用函數,接受單一整數而不是單元素元組;對於所有輸出都是純量的廣義通用函數,可以省略 (空的) 輸出元組。因此,對於適用於內積的 (i),(i)->() 簽名,可以傳入 axes=[0, 0] 以指示向量儲存在兩個輸入引數的第一個維度中。

作為與縮減類似的廣義通用函數 (即,在單一共享核心維度 (例如上述內積範例) 上運作) 的快捷方式,可以傳遞 axis 參數。這相當於傳入 axes,其中所有引數對於該核心維度都具有相同的條目 (例如,對於上述範例,axes=[(axis,), (axis,)])。

此外,與縮減類似,對於輸入都具有相同核心維度數且輸出沒有核心維度的廣義通用函數,可以傳遞 keepdims 以在輸出中保留大小為 1 的維度,從而允許針對原始輸入進行適當的廣播。可以使用 axes 控制額外維度的位置。例如,對於內積範例,keepdims=True, axes=[-2, -2, -2] 將作用於內積範例,keepdims=True, axis=-2 將作用於輸入引數的倒數第二個維度,並在輸出中的該位置保留大小為 1 的維度。

float128 值現在在 ppc 系統上正確列印#

先前,在 ppc 上列印 float128 值存在錯誤,因為未考慮這些系統上的特殊雙精度浮點格式。float128 現在以正確的捨入和唯一性列印。

對 ppc 使用者的警告:如果 glibc 版本 <= 2.23,您應該升級 glibc,尤其是在使用 float128 的情況下。在 ppc 上,這些版本中 glibc 的 malloc 經常錯誤對齊已配置的記憶體,這在使用 float128 值時可能會導致 numpy 崩潰。

新的 np.take_along_axisnp.put_along_axis 函數#

當用於多維陣列時,argsortargminargmaxargpartition 回傳難以用作索引的陣列。take_along_axis 提供了一種簡單的方法來使用這些索引在陣列中查找值,因此

np.take_along_axis(a, np.argsort(a, axis=axis), axis=axis)

np.sort(a, axis=axis)

np.put_along_axis 作為在陣列中寫入這些索引的雙重運算。