WebニューラルネットワークAPI

W3C勧告候補草案,

この文書の詳細
このバージョン:
https://www.w3.org/TR/2026/CRD-webnn-20260521/
最新公開バージョン:
https://www.w3.org/TR/webnn/
編集者草案:
https://webmachinelearning.github.io/webnn/
以前のバージョン:
履歴:
https://www.w3.org/standards/history/webnn/
実装報告書:
https://wpt.fyi/results/webnn?label=master&label=experimental&aligned&q=webnn
テストスイート:
https://github.com/web-platform-tests/wpt/tree/master/webnn
フィードバック:
GitHub
仕様内インライン
編集者:
Ningxin Hu (Intel Corporation)
Dwayne Robinson (Microsoft Corporation)
元編集者:
Chai Chaoweeraprasit (Microsoft Corporation)
その他:
実装状況, 解説, サンプル

概要

この文書は、ニューラルネットワーク推論のハードウェアアクセラレーションのための専用の低レベルAPIについて説明する。

この文書の位置付け

この節では、公開時点におけるこの文書の位置付けについて説明する。現在のW3C 公開文書およびこの技術報告書の最新改訂版の一覧は、W3C標準および草案インデックスで確認できる。

この文書は、Web Machine Learning Working Group により、勧告 トラックを用いた勧告候補草案として公開された。

勧告候補としての公開は、W3Cおよびその会員による承認を意味するものではない。勧告候補草案は、ワーキンググループが後続の勧告候補スナップショットに含めることを意図している、以前の勧告候補からの変更を統合する。

これは草案文書であり、いつでも他の文書によって更新、置換、または廃止される可能性がある。この文書を進行中の作業以外として引用することは適切ではない。

Web Machine Learning Working Groupは、グループがまだ対処していないすべてのバグ 報告の一覧を管理している。 未解決の課題について、提案仕様テキストを含むプルリクエストを強く推奨する。

この文書は、 W3C特許ポリシーの下で運営されるグループにより作成された。 W3Cは、そのグループの成果物に関連して行われた あらゆる 特許開示の公開一覧を管理している。そのページには、 特許を開示するための手順も含まれている。ある個人が、 必須 クレームを含むとその個人が考える特許について実際の知識を有している場合、 W3C特許ポリシーの第6節に従ってその情報を開示しなければならない。

この文書は、2025年8月18日版W3C Process Documentにより管理される。

2024年4月11日の勧告候補スナップショット11 April 2024から2026年1月22日の22 January 2026までの間に、WebNN 仕様は100件を超える重要な変更を伴う大幅な進化を遂げた。特に注目すべき 追加には、transformersサポートを強化するための第3波の演算子、バッファ 共有のためのMLTensor API、および新しい抽象デバイス選択メカニズムが含まれる。APIサーフェスは近代化され、 より広範な実装経験および開発者からのフィードバックに基づいて相互運用性の改善が行われた。この仕様バージョンでは、 フィンガープリンティング緩和を含むセキュリティおよびプライバシーの考慮事項が強化され、 新しいアクセシビリティの考慮事項も追加されている。これらの変更は、開発者エルゴノミクスの改善、より広いバックエンド 互換性、および標準準拠により、製品対応に向けた仕様の成熟を反映している。詳細については、§ 14 変更点を参照。

この文書は随時保守および更新される。この文書の一部は進行中の作業であり、 今後の勧告候補草案およびスナップショットの改訂にさらなる改善が反映されることが期待される。

勧告案への移行を要求する前に、 ワーキンググループは次のことを実証するよう努める。

1. はじめに

Web Neural Network APIは、プラットフォーム固有の能力に縛られることなく、 オペレーティングシステムおよび基盤となるハードウェアプラットフォームの機械学習能力を利用する、 Web向けのハードウェア非依存の抽象化レイヤーを定義する。この抽象化レイヤーは、 主要な機械学習JavaScriptフレームワークの要件に対応し、さらにML分野に精通したWeb開発者が ライブラリの助けを借りずにカスタムコードを書けるようにもする。

図解付きの導入については、解説を参照されたい。

2. ユース ケース

2.1. アプリケーションユースケース

この節では、ニューラルネットワーク推論ハードウェアアクセラレーションの アプリケーションレベルのユースケースを例示する。これらのユースケースにおけるすべてのアプリケーションは、 事前学習済みの深層ニューラルネットワーク(DNN)[models]上に構築できる。

注記: ここで説明するユースケースの一部は、 その性質上、プライバシー侵害的であることに注意されたい。そのようなユースケースにAPIを使用することを 計画している開発者は、そのAPIがユーザーの利益のために、ユーザーが理解し承認する目的で使用されることを 保証すべきである。開発者は、 Ethical Principles for Web Machine Learning [webmachinelearning-ethics]を適用し、 透明性、データ最小化、ユーザー制御などの適切なプライバシーリスク緩和策を実装すべきである

注記: § 3 アクセシビリティの 考慮事項は、これらのユースケースのアクセシビリティを改善する方法についての指針を提供する。

2.1.1. 人物検出

ユーザーがWebベースのビデオ会議アプリケーションを開いているが、一時的に 部屋から離れている。アプリケーションは、カメラ入力フレーム内で人物を含む領域を検出するために、 (例えば、単一のDNNを使用する[SSD][YOLO]などの物体検出手法を用いた) 物体検出を使用して、ユーザーがPCの前にいるかどうかを監視している。

彼女が戻ってくると、アプリケーションは自動的に彼女を検出し、 他のオンラインユーザーに彼女が現在アクティブであることを通知する。

2.1.2. セマンティックセグメンテーション

ユーザーは、オフィスに空いている会議室がないため、自席からWebベースのビデオ会議アプリケーションで 電話会議に参加する。電話会議中、彼女は自分の部屋や背景にいる人々が 見えることを望まない。他の人々および周囲のプライバシーを保護するために、 アプリケーションは[DeepLabv3+][MaskR-CNN] または[SegAny]などの機械学習モデルを実行して、 画像を意味的にセグメントへ分割し、 他の人々および背景を表すセグメントを別の画像で置き換える。

2.1.3. 骨格検出

Webベースのビデオ会議アプリケーションは、[PoseNet]などの リアルタイム人体姿勢推定を可能にする機械学習モデルを実行して、ユーザーの骨格姿勢を追跡し、 彼女のジェスチャーおよびボディランゲージを認識する。彼女が手を挙げると、 マイクは自動的にミュート解除され、電話会議で発言を開始できる。

2.1.4. 顔認識

会議室には複数の人がおり、彼らはWebベースのビデオ会議アプリケーションを使用して オンライン会議に参加する。アプリケーションは、(例えば[SSD]などの物体検出手法を用いた)物体検出を使用して 参加者の顔を検出し、2つの顔が同一であるかどうかを検証する[FaceNet]などの機械学習モデルを実行して、 各顔が前回の会議に存在していたかどうかを確認する。

2.1.5. 顔ランドマーク検出

ユーザーは、オンライン眼鏡店で自分に美しく合う新しい眼鏡を探したい。オンラインストアは、 [FAN]のような Face Alignment Networkなどの機械学習モデルを実行して、目、鼻、口などの顔ランドマークを検出する Webベースの試着シミュレーターを提供する。彼女が眼鏡を選択すると、シミュレーターは 彼女の顔画像上で検出された目の位置に、選択された眼鏡を適切にレンダリングする。

2.1.6. スタイル転送

ユーザーはオンラインストアで化粧品を探しており、どの色が自分の顔に合うかを考えている。 オンラインストアは化粧品のサンプル顔メイク画像を表示し、 [ContextualLoss]または[PairedCycleGAN] のような機械学習モデルを実行して、サンプルメイク画像のメイクスタイルを彼女の顔画像に転送する メイクシミュレーターを提供する。彼女はシミュレーターにより、選択したメイクが 自分の顔でどのように見えるかを確認できる。

2.1.7. 超解像

Webベースのビデオ会議は相手からビデオストリームを受信しているが、 ネットワーク輻輳によりビデオの解像度が低下している。知覚される映像品質の低下を防ぐために、 アプリケーションは[SRGAN]などの 超解像用機械学習モデルを実行し、より高解像度のビデオフレームを生成する。

2.1.8. 画像キャプション生成

アクセシビリティを向上させるために、Webベースのプレゼンテーションアプリケーションは、 プレゼンテーションスライドの説明語を予測する [im2txt] などの機械学習モデルを実行して、自動画像キャプション生成を提供する。

2.1.9. テキストから画像への生成

画像は現代のWeb体験の中核をなす。プライバシーを保護する方法でテキスト入力に基づいて画像を生成する能力は、 Webアプリケーションおよびコンテンツの視覚的なパーソナライズと適応を可能にする。例えば、Web アプリケーションは、Webページ上の自然言語による説明、またはテキストプロンプト内でユーザーが提供した説明を 入力として使用し、そのテキスト説明に一致する画像を生成できる。潜在拡散モデルアーキテクチャ [LDM]によって可能になるこのテキストから画像への生成ユースケースは、 追加のテキストから画像への生成ユースケースの基礎を形成する。例えば、Webページ上の既存画像の一部を 新たに生成されたコンテンツを用いて選択的に変更するインペインティング、またはその逆で、 元画像を本来の寸法を超えて拡張し、空いた領域を生成されたコンテンツで埋めるアウトペインティングがある。

2.1.10. 機械翻訳

さまざまな国の複数の人々が、Webベースのリアルタイムテキストチャットアプリケーションを通じて会話している。 アプリケーションは、すべてのテキストを別の言語に翻訳する[GNMT]または[OpenNMT]などの 機械学習モデルを使用して、彼らの会話を翻訳する。

2.1.11. 感情分析

ユーザーはWebベースのリアルタイムテキストチャットアプリケーションを通じて友人と会話しており、 友人の顔を見ることができないため、友人がどのように感じているかを知りたいと思っている。 アプリケーションは、入力テキストから感情を推論する[DeepMoji] などの機械学習モデルを使用して友人の感情を分析し、 推定された感情を表す絵文字を表示する。

2.1.12. 動画要約

Webベースのビデオ会議アプリケーションは受信したビデオストリームを録画しており、 保存する録画ビデオデータを削減する必要がある。アプリケーションは、 [Video-Summarization-with-LSTM]などの 動画要約用機械学習モデルを使用して、録画ビデオの短縮版を生成する。

2.1.13. ノイズ抑制

Webベースのビデオ会議アプリケーションは受信した音声ストリームを録音しているが、 通常、背景ノイズは至るところに存在する。アプリケーションは、ビデオ会議における音声体験を向上させるために、 赤ちゃんの泣き声や犬の吠え声のような背景の動的ノイズを抑制する目的で、 [RNNoise]などの再帰型ニューラルネットワークを用いた リアルタイムノイズ抑制を活用する。

2.1.14. 音声認識

音声認識はspeech to textとしても知られ、話された言語を認識して テキストへ変換することを可能にする。音声認識のアプリケーション例には、 文字起こし、自動翻訳、マルチモーダルインタラクション、リアルタイムキャプション、およびバーチャルアシスタントが含まれる。 音声認識は聴覚コンテンツのアクセシビリティを向上させ、そのようなコンテンツを プライバシーを保護する方法でテキスト形式により操作することを可能にする。一般的な ユースケースの例には、リアルタイムキャプションを使用した動画視聴やオンライン会議への参加が含まれる。 [Whisper]などのモデルは、 精度と堅牢性の点で人間に近づいており、そのようなユースケースのアクセシビリティを向上させる上で適している。

2.1.15. テキスト生成

大規模言語モデル(LLM)により、テキスト列における次の項目を予測する一般的能力が 必要とされるタスクを実行できる、さまざまなテキスト生成ユースケースが可能になる。この種のモデルは、 テキストを翻訳し、テキスト入力に基づいて質問に答え、より大きな本文を要約し、または テキスト入力に基づいてテキスト出力を生成できる。LLMは、RNN、CNN、またはLSTMアーキテクチャに基づく 古いモデルと比較してより良い性能を可能にし、この節で説明する他の多くのユースケースの 性能をさらに向上させる。 LLMの例には、[t5-small][m2m100_418M][gpt2]、および[llama-2-7b]が含まれる。

2.1.16. フェイク動画の検出

ユーザーはWeb上で“deepfake”によって生成されたリアルなフェイク動画にさらされる。 フェイク動画は、話者の顔を大統領の顔に入れ替えて、ユーザーを政治的に扇動したり、 ユーザーの意見を操作したりする可能性がある。[FaceForensics++]などのdeepfake検出アプリケーションは動画を分析し、 ユーザーをフェイク動画または画像から保護する。彼女がWeb上でフェイク動画を視聴したとき、 検出アプリケーションはリアルタイムでその不正な動画を警告する。

2.2. フレームワークユースケース

この節では、ニューラルネットワーク推論ハードウェアアクセラレーションのための専用低レベルAPIに関する フレームワークレベルのユースケースを収集する。機械学習フレームワークがWeb Neural Network API(WebNN API)の主要な利用者となり、WebNN APIを通じて公開される低レベルの詳細は 一般的なWeb開発者から抽象化されることが期待される。しかし、機械学習に特定の関心と能力を持つWeb開発者が、 より高レベルのMLフレームワークではなくWebNN APIと直接やり取りしたいと考えることも期待される。

2.2.1. カスタムレイヤー

Webアプリケーション開発者は、WebNN API上でDNNモデルを実行したい。しかし、 [LeakyReLU][ELU]などの 一部の活性化関数がWebNN APIに含まれていないことに気付いた。この問題に対処するために、彼女は WebNN API上に追加の活性化関数のカスタムレイヤーを構築する。 カスタムレイヤーの範囲には、活性化だけでなく畳み込み、正規化なども含まれ得ることに注意されたい。

2.2.2. ネットワーク結合

WebアプリケーションはDNNモデルを使用し、その上位の畳み込み層および下位の全結合層のモデルデータは 別々のファイルに保存される。これは、全結合層のモデルデータがサーバー側での ファインチューニングにより定期的に更新されるためである。

したがって、アプリケーションは最初に両方の部分モデルファイルをダウンロードし、 それらを単一のモデルに結合する。モデルが更新されると、アプリケーションはモデルの ファインチューニング済み部分をダウンロードし、全結合層のみをそれで置き換える。

2.2.3. 性能適応

Webアプリケーション開発者は、モバイルデバイス上での自分のDNNモデルの性能について懸念している。 彼女は、GPUアクセラレーションを備えていないモバイルデバイスでは実行が遅すぎる可能性があることを確認した。 この問題に対処するために、彼女のWebアプリケーションはWebNN APIを参照してアクセラレーションが利用可能かどうかを確認し、 アクセラレーションのないデバイスに対して警告を表示できるようにする。

数週間後、彼女はCPU上でも実行できる小型のDNNモデルを開発した。 CPU実行に対応するために、彼女はアプリケーションを修正し、 CPUのみのデバイスの場合にその小型モデルをロードするようにする。

2.2.4. 演算レベル実行

JavaScript MLフレームワークは、MLモデルのロード、解釈、および実行を担う。モデルの 実行フェーズ中、フレームワークはモデルの演算を反復し、各演算を CPU、GPU、またはMLアクセラレーターのようなハードウェアデバイス上で実行する。デバイス間の不要なデータコピーを避けるため、 フレームワークは演算を実行する同じデバイスを選択する。畳み込み2Dや行列乗算などの 計算集約的な演算では、フレームワークはWebNN APIを使用して、選択されたデバイスで利用可能な ML固有のアクセラレーションによりそれを実行する。

2.2.5. リアルタイム動画処理との統合

WebRTCベースのビデオ会議のユーザー体験は、リアルタイム動画処理を使用して強化される。例えば、 § 2.1.2 セマンティックセグメンテーションモデルを使用して実装された背景ぼかしは、 ユーザーのライブカメラ映像内の背景をぼかす。このユースケースの性能要件を満たすために、 WebNN APIは、メディアパイプラインを構成する他のWeb APIのプリミティブと統合し、 WebNN APIベースのリアルタイム動画ストリーム変換を可能にする。

3. アクセシビリティの考慮事項

この節は、ニューラルネットワーク推論ハードウェアアクセラレーションによって可能になる § 2.1 アプリケーションユースケースのアクセシビリティを改善する方法について、 Web作者に指針を提供する。この指針は、本仕様で概説される特定のユースケースを超えて一般化されるものであり、 Web作者は、さらなるアクセシビリティ指針として[wcag]を、倫理原則の文脈における デジタルアクセシビリティについては§ 6 倫理的考慮事項を参照することが推奨される。

§ 2.1.8 画像キャプション生成は、 キャプションがスクリーンリーダーおよびその他の支援技術(AT)ユーザーに提示されることを保証することで改善できる。 Web作者は、生成された画像キャプションが、それぞれの画像に意味的に関連付けられることを保証することが推奨される。 これは、標準のalt属性を介して、または説明が初期ページロード時に更新されるか、 あるいは後からユーザー操作の結果として更新されるかに応じた他の手段によって行うことができる。

§ 2.1.11 感情分析は、ユーザーを誤ってラベル付けし、 したがって誤分類する可能性があり、差別的な体験につながり得る。Web作者は、信頼度スコアを公開し、 ユーザーにその機能をオフにする選択肢を与えることが推奨される。

§ 2.1.13 ノイズ抑制は、強いフィルターを用いると 構音障害のあるユーザーの発話を消し去り、キャプションおよび認識を失敗させる可能性がある。Web作者は、 バイパスまたは感度制御を公開し、ライブキャプションが有効な場合にノイズ抑制を固定的に組み込まないことが推奨される。

§ 2.2.5 リアルタイム動画処理との統合では、 セグメンテーションにより実現される背景ぼかしが気を散らす要素を取り除くのに役立つが、 読唇やライブキャプションを損なうほどの遅延を追加する可能性がある。Web作者は、 ユーザー向けにキーボードおよびスクリーンリーダーで操作可能な“背景ぼかしオン/オフ”コントロールを、 他のアクセシビリティ/メディア設定の近くに提示する機能を提供することが推奨される。

§ 7.2 デバイス選択により、Web作者は 実行速度および消費電力に関する設定を示すことができる。実装者は、ブラウザーUIで Web作者のヒントをユーザーが上書きできるようにすることが推奨される。これにより、特に携帯型AACや 視線入力の環境において、低性能またはバッテリーに敏感なデバイス上の人々が、 キャプションおよびその他の重要なアクセシビリティ機能を応答性の高い状態に保てるようにする。

4. セキュリティの考慮事項

この仕様は、ニューラルネットワーク推論ハードウェアアクセラレーションのための低レベルAPIを定義する。このAPIは、 ユーザーのコンピューターへの低レベルアクセスを与えるため、強力な機能[POWERFUL-FEATURES]と見なされる。強力な機能に対する認証および機密性の期待を 満たし、中間者攻撃を防止するために、この仕様で定義されるすべてのインターフェイスはセキュアコンテキストでのみ利用可能である。

このAPIは、§ 7.5 権限ポリシー統合を用いて、すべてのクロスオリジンフレームで デフォルトで無効化される。これにより、埋め込みページが許可を与えるポリシーを明示的に設定しない限り、 サードパーティコンテンツがこのAPIを使用することを防止する。

このAPIは、WebGPU仕様で定義されるGPUDeviceから MLContextを作成できるようにする。このコンテキストのセキュリティ特性に関する 詳細については、WebGPU Security Considerationsを参照。

このAPIは、GPU、CPU、および専用MLアクセラレーターハードウェアにまたがる抽象化を提供する。GPUを使用する場合、WebGPUと同様のサービス拒否に関する考慮事項が適用される。 CPUまたは専用MLアクセラレーターを使用する場合、潜在的なリソース競合の種類は異なり、緩和策は実装および構成に依存する。 実装は、サイトが不公平な量のシステムリソースを使用することを防ぐために、プラットフォームで利用可能なあらゆる仕組みを使用すべきである。 これらの計算ユニットは共有リソースであり、あらゆる計算APIの使用は、高負荷状態のシステム全体の性能に影響する。

グラフが完全に構築されコンパイルされると、グラフ内の各演算への入力形状が推論され、確定される。 境界チェックは、実データに対してグラフを実行する計算メソッドが呼び出されたときに行われる。 この段階より前に、実データがコンパイル済みグラフに束縛されることはない。その時点までに推論済みのデータ形状に対して 適切な境界チェックが行われるよう保証することは、実装の責任である。

実装者への指針として、 境界外アクセスを受けやすい演算を文書化する。

実装は、定数と見なされるデータの変更に基づく制御フロー攻撃を防御しなければならない。 例えば、基盤プラットフォームの最適化は、計算全体を通じて重みが変更されないと仮定する場合がある。 APIが計算中に重みを保持するバッファの内容変更を許す場合、それらの最適化の仮定は無効になり、 基盤プラットフォームで未定義の動作を引き起こすことになる。このAPIは、常にバッファをコピーまたは転送することで、 スクリプトからのこの種の攻撃を緩和するが、実装は、定数と仮定されるデータのプロセス分離など、 追加の防御策を検討すべきである。

将来への備えとして、API設計は、互換性を壊すことなく、汎用的にエミュレート可能な特定の演算を セキュリティ、性能、またはその他の理由により非推奨にできるようにしている。これは、この仕様で定義される より小さなプリミティブ演算の観点から定義される高レベル関数によって可能になる。これにより、高レベル関数の ネイティブ実装をポリフィル実装で置き換えることが可能になる。

レンダラーを実行するプロセス間で CPUが共有されている現在の状態を考慮し、サイドチャネル攻撃の実現可能性を調査する。

攻撃者が欠陥を含む可能性のある特定の実装を標的にできないようにするために、§ 7.2 デバイス選択メカニズムはヒントにすぎず、 具体的なデバイス選択は実装に委ねられる。例えば、ユーザーエージェントは、既知の脆弱性を持つデバイス上では モデルを決して実行しないことを選択できる。さらなる緩和策として、デバイス列挙メカニズムは定義されていない。

ヒント付けは懸念を部分的に 緩和する。追加の緩和策を調査する。

API設計は、コンパイル済み計算グラフの攻撃対象領域を最小化する。各種演算をホストするMLGraphBuilder インターフェイスはデータ定義APIであり、そのため何も実行せず、データを構築するだけである。 その結果、攻撃の可能性は、MLContext.dispatch() メソッドを呼び出して実行する前に、データをグラフに束縛するときに限定される。これにより、実装者はMLContext.dispatch() メソッドの堅牢化に集中できる。例えば、データの境界を尊重し、境界が守られない場合に適切に失敗することを 確実にすることである。

高解像度時刻を測定するための専用Web APIは、解像度の低減、ジッターの追加、濫用の検出、API呼び出しの スロットリングなどの技術を用いて、タイミング攻撃を緩和する[hr-time-3]。 WebNN実装の実際の展開では、タイミング攻撃を実用的でないものにするのに十分なジッターがもたらされる可能性が高い (例えばIPCを使用するため)が、実装者はタイミング攻撃について検討し、自らの実装に対してテストすることが推奨される。

注記: Unicodeシーケンスに関連するセキュリティリスクは、 label USVString 定義の文脈で論じられる。

4.1. 新しい演算に関するガイドライン

この節は非規範的である。

この仕様で定義される演算が安全に実装できる形で形成されることを保証するために、 この節には、実装上の問題の可能性を低減するために演算がどのように定義されることが期待されるかについての ガイドラインが含まれる。これらのガイドラインは、業界のベストプラクティスに合わせて時間とともに進化することが期待される。

一般に、新機能を追加する際は、Technical Architecture GroupおよびPrivacy Interest Groupによる[security-privacy-questionnaire]に 文書化されているセキュリティおよびプライバシーへの影響を常に考慮すること。

5. プライバシーの考慮事項

このAPIは、機密性の高いユーザーデータをブラウザーのサンドボックス内に保持することにより、 クラウドベースの推論代替手段に比べてプライバシーを向上させる。画像、音声、動画ストリーム、 その他の個人情報などの入力データはユーザーのデバイスを離れることがなく、リモートサーバーへのデータ送信や サードパーティによるデータ処理に伴うリスクを排除する。

しかし、ハードウェアアクセラレーション能力と密接に相互作用する強力なローカル計算APIとして、 WebNN APIは性能最適化とプライバシー保護のバランスを取る必要がある。このAPIには、有効な 機械学習推論能力を引き続き可能にしつつ、フィンガープリンティングを緩和するための複数の プライバシー保護措置が含まれる。

5.1. フィンガープリンティング

設計上、このAPIは、特定された§ 2 ユースケースに、最良の性能と結果の信頼性で対応するために必要な最小限の情報を 公開することを目指す。第一に、このAPIは標準化を通じてフィンガープリンティングを緩和する。すなわち、 多様なプラットフォームAPI間で一貫した動作を定義し、適合実装間で基盤ハードウェアの差異に関する情報漏えいを 最小化することによってである。これは次のものにより達成される。

全体的な設計は、必要な機能を提供しながら、実装が異なるプラットフォーム間で一貫したインターフェイスを維持することを保証する。 プラットフォーム固有の詳細を抽象化することにより、基盤となるアクセラレーションがCPU、GPU、または専用MLハードウェアの いずれによって提供されるかにかかわらず、APIはプライバシーを保護する予測可能な動作を提供できる。

注記: MLContextOptions は活発に開発中であり、その設計は、さらなる実装経験およびより広いWebコミュニティからの新しいユースケースに基づいて 変更されることが期待される。

MLGraph.devices API拡張は、グラフが完全に構築されコンパイルされた後に、実行のために選択された実際のデバイスを 公開するものとして提案されている。このAPI拡張のプライバシーへの影響は調査中である。[Issue #836]

5.2. 実行時間分析

演算のタイミング特性は、基盤ハードウェア性能に関する間接的な情報を提供し得る。これはあらゆる計算APIに固有の特徴である。 特定の状況では、実行時間分析により、別の基盤プラットフォームと比較した基盤プラットフォームのニューラルネットワーク ハードウェアアクセラレーション能力の性能を間接的に明らかにできる場合がある。タイミング攻撃に関するさらなる議論については、 § 4 セキュリティの考慮事項も参照。

注記: このグループは、提案されている実行時間分析 フィンガープリンティングベクトルおよび緩和策について、さらなる意見を歓迎している

5.3. WebGPUとの比較

WebGPUとは異なり、このAPIはカスタムシェーダー記述を本質的にサポートしない。その結果、シェーダーキャッシュや その他の永続データに依存するタイミング攻撃を受けにくい。APIは、ブラウザーまたは基盤OSの既存のシェーダーおよび より低レベルのプリミティブの上に構築される。GPUDevice とやり取りするWeb開発者は、WebGPU コンパイルキャッシュに関する考慮事項を認識していることが期待される。

WebGPU APIは、プライバシー上の考慮事項としてマシン固有のアーティファクトを特定している。 同様に、WebNN APIの計算ユニットスケジューリングは、特定の状況下でフィンガープリントを導入する可能性がある。 しかし、WebGPUと同様に、そのようなフィンガープリントは各ベンダーのほとんどまたはすべてのデバイスで同一であり、 懸念を緩和する。さらに、そのようなアーティファクトをさらに排除するためにソフトウェア実装を使用できる。

一般に、このAPIの実装者は、該当する場合、WebGPU Privacy Considerationsを 自らの実装に適用することが期待される。

6. 倫理的考慮事項

ワーキンググループは、Web上で機械学習を使用することに関連する倫理的問題の文書化を開始しており、 その規範仕様が考慮すべき緩和策を特定する助けとしている。ワーキンググループは、専用のGitHubリポジトリを通じて より広いコミュニティからの貢献を受け入れる、Ethical Principles for Web Machine Learning文書[webmachinelearning-ethics]を公開し、維持している。

7. プログラミングモデル

7.1. 概要

ニューラルネットワークの中心には、数学的演算からなる計算グラフがある。 これらの演算は、コンピュータービジョン、自然言語処理、およびロボティクスにおける 現代の機械学習技術の構成要素である。 WebNN APIは、ニューラルネットワークの計算グラフを構築、コンパイル、および実行するための仕様である。

MLGraph インターフェイスは、不変であるコンパイル済み計算グラフ(すなわちモデル)を表す。

MLGraphBuilder インターフェイスは、計算グラフ(そのグラフ)を 構築するビルダー(ファクトリー)として機能し、その後コンパイルされてMLGraphが作成される。

WebNNにおいて、計算グラフは、データに作用し、グラフのノードである演算子から構成される。MLOperandは、 計算グラフ内を流れるデータの表現であり、グラフの辺である。MLOperandには、 推論のための計算グラフ入力値、推論に使用される定数(学習済み重みを含む)、 推論中に計算される中間値(しばしば活性化と呼ばれる)、および推論の出力値が含まれる。 演算子入力は、1つ以上のMLOperandである。 演算子出力は、1つ以上のMLOperandである。演算子には、その動作を制御する演算子固有の パラメーターがあり、これには0個以上の活性化関数が含まれ得る。

MLGraphBuilder インターフェイスの重要な部分は、gemm()relu() のようなメソッドであり、これらは計算が実行されるときに入力データに対して実行する実際の演算を表す演算子を作成し、 その演算子を保持する新しいMLOperandを 返す。MLOperandを作成するメソッドは、 任意の入力および活性化を演算子に接続する。 各メソッド呼び出しは、他のいかなるMLOperandの値も変更せずに、 個別の新しい値を返す。

演算子は、ラベル、すなわち例外メッセージなどの診断に含まれ得る文字列を持つ。演算子が作成されると、そのラベル実装定義の方法で初期化され、渡されたlabelを含む場合がある。

dispatch()中に エラーを報告する仕組みの追加を検討する。 [Issue #778]

推論時には、すべてのMLOperandが テンソル(実データ)に束縛される。テンソルは本質的に多次元配列である。テンソルの表現は 実装依存であるが、通常は何らかのバッファ(メモリ)に格納された配列データと、 配列データを記述するメタデータ(その形状など)を含む。

計算グラフ内の演算は関数的意味論を持つ。これにより、実装は複数のテンソル間で配列データを 共有できる可能性がある。例えば、reshapeやsliceなどの演算の実装は、 入力テンソルと同じバッファを共有する入力テンソルのビューを返す場合がある。 (reshapeの場合はデータ全体が共有される一方、sliceの場合は入力データの一部が共有される。) 実装は、上記のようなビューを中間値に使用してもよい。

実行の前に、1つ以上の指定された出力を計算するために使用される計算グラフは、 変換、コンパイル、および最適化される必要がある。コンパイル段階の主な目的は、 演算やループの融合など、2つ以上の演算にまたがる最適化を可能にすることである。 ユーザーエージェントは、グラフ変換中にこれらの最適化を行ってもよい。

MLGraphBuilder.build() メソッドは、呼び出しスレッドをブロックせずにバックグラウンドでグラフをコンパイルし、Promiseを返す。 そのPromiseはMLGraphに解決される。各MLGraphBuilderは、 最大1つのMLGraphを構築できる。

MLGraphの 基盤実装は、MLGraphBuilder演算子およびMLOperandに対応する、 演算子およびオペランドのプラットフォーム固有表現から構成されるが、それらはスクリプトからは見えず、 スクリプトにより構築されたグラフの合成または分解である場合がある。

MLGraphが 構築されると、MLContext.dispatch() メソッドは、CPU実行の場合は別個のワーカースレッド内の並列タイムライン上で、またはGPUコマンドキュー内のGPUタイムライン上で、 グラフの実行を非同期に行う。このメソッドは、実際の実行が別のタイムラインにオフロードされる間、 呼び出しスレッドをブロックせずに直ちに返る。呼び出し側はMLNamedTensorsを使用して 入力値を供給し、入力MLOperandを その値に束縛する。呼び出し側はまた、出力MLOperand用のMLNamedTensorsも 供給し、成功した場合にはそこにグラフ実行の結果が格納される。その結果は、MLContext.readTensor(tensor) メソッドを使用してスクリプトへ読み戻すことができる。この種類の実行は、CPU、GPU、およびNPUデバイスをサポートする。

7.2. デバイス選択

MLContext インターフェイスは、ニューラルネットワーク実行のグローバル状態を表す。重要なコンテキスト状態の1つは、 リソースを管理し、ニューラルネットワークグラフのコンパイルおよび最終的な実行を容易にする基盤実行デバイスである。 MLContextOptionsを用いる デフォルトの作成方法に加えて、MLContextは、 アプリケーションで既に使用されている特定のGPUDeviceからも 作成できる。

GPUコンテキストが、システムメモリ内の定数または入力をArrayBufferViewとして 持つグラフを実行する状況では、入力内容はシステムメモリからGPUメモリへ自動的にアップロードされ、 グラフ実行の最後にArrayBufferView 出力バッファのシステムメモリへダウンロードされる。このデータのアップロードおよびダウンロードサイクルは、 GPUの場合のように、実行デバイスがデータをシステムメモリから外へ、そして再びシステムメモリ内へコピーすることを 必要とする場合にのみ発生する。デバイスがCPUデバイスである場合には発生しない。さらに、グラフ実行の結果は 既知のレイアウト形式である。グラフ内の中間結果では、ネイティブなメモリアクセスパターン向けに実行が最適化される場合があるが、 呼び出し側の観点から期待される動作を維持するために、グラフの最後の演算の出力は、グラフの最後で内容を 既知のレイアウト形式に戻さなければならない。

MLContextMLContextOptionsで 作成される場合、ユーザーエージェントはこれらのオプションを考慮して、基盤実行デバイスを選択し作成する。

基盤プラットフォームに応じて、ユーザーエージェントはCPU、NPU、およびGPUデバイスの異なる組み合わせを選択してもよい

この設計の履歴および根拠については、デバイス 選択の解説を参照。

7.3. 演算子

この節は非規範的である。

WebNN APIは、主要な§ 2.1 アプリケーションユースケースに対応する、 よく知られたCNNおよびRNN、transformer、生成モデルに必要な一連の演算子を定義する。各演算子の詳細は、 この仕様の規範的な節で、演算子名のアルファベット順に定義される。これらの演算子は、APIサーフェスの機能的概要を 示すため、次の非規範的な表において、その機能に基づくカテゴリに分類される。

注記: 一部の演算子は複数のカテゴリに属する。 例えば、clamp() は数学関数であると同時に、活性化としても使用される。

カテゴリ別の演算子
カテゴリ 演算子​
テンソル作成 input(), constant()
テンソル操作 concat(), expand(), gather(), gatherElements(), scatterElements(), gatherND(), scatterND(), where(), pad(), reshape(), slice(), split(), transpose(), resample2d(), reverse(), tile(), triangular()
テンソル量子化 quantizeLinear(), dequantizeLinear()
テンソルキャスト cast()
数学 add(), sub(), mul(), div(), max(), min(), clamp(), pow(), abs(), ceil(), cos(), erf(), exp(), floor(), identity(), log(), neg(), reciprocal(), sin(), sqrt(), tan(), tanh(), sign(), clamp()
論理 equal(), notEqual(), greater(), greaterOrEqual(), lesser(), lesserOrEqual(), logicalNot(), logicalAnd(), logicalOr(), logicalXor()
行列乗算 matmul(), gemm()
畳み込み conv2d(), convTranspose2d()
プーリング averagePool2d(), l2Pool2d(), maxPool2d()
活性化 clamp(), elu(), gelu(), hardSigmoid(), hardSwish(), leakyRelu(), linear(), prelu(), relu(), sigmoid(), softmax(), softplus(), softsign(), tanh()
正規化 batchNormalization(), instanceNormalization(), layerNormalization()
リダクション argMin(), argMax(), reduceL1(), reduceL2(), reduceLogSum(), reduceLogSumExp(), reduceMax(), reduceMean(), reduceMin(), reduceProduct(), reduceSum(), reduceSumSquare(), cumulativeSum()
再帰型ニューラルネットワーク gruCell(), gru(), lstmCell(), lstm()

7.4. タスクソース

MLタスクソースは、 MLGraphの非同期コンパイルおよび実行、ならびに MLContextの作成に関連するすべてのタスクに使用されるタスクソースである。

グローバルオブジェクトglobalおよび一連の手順 stepsが与えられたとき、MLタスクを キューに入れるには、globalおよび stepsとともに、MLタスクソース上でグローバルタスクをキューに入れる

7.5. 権限ポリシー統合

この仕様は、文字列 "webnn"により 識別されるポリシー制御機能を定義する。 そのデフォルト許可リスト'self'である。

8. API

8.1. navigator.mlインターフェイス

MLオブジェクトは、 Window およびWorkerGlobalScope コンテキストにおいて、それぞれNavigator およびWorkerNavigator インターフェイスを通じて利用可能であり、navigator.mlを介して公開される。

interface mixin NavigatorML {
  [SecureContext, SameObject] readonly attribute ML ml;
};
Navigator includes NavigatorML;
WorkerNavigator includes NavigatorML;

8.2. ML インターフェイス

enum MLPowerPreference {
  "default",
  "high-performance",
  "low-power"
};

dictionary MLContextOptions {
  MLPowerPreference powerPreference = "default";
  boolean accelerated = true;
};

[SecureContext, Exposed=(Window, Worker)]
interface ML {
  Promise<MLContext> createContext(optional MLContextOptions options = {});
  Promise<MLContext> createContext(GPUDevice gpuDevice);
};

8.2.1. MLContextOptions

注記: MLContextOptions は活発に開発中であり、その設計は、さらなる実装経験およびより広いWebコミュニティからの新しいユースケースに基づいて 変更されることが期待される。ワーキンググループは、フォールバックデバイス、優先順位付きの複数デバイス、 または特定デバイスの除外の定義を可能にする追加のAPI制御を検討している。議論中のその他の考慮事項には、 エラー処理、最終的なフォールバック、および量子化演算子が含まれる。これらの設計上の考慮事項について、 Web開発者、ライブラリ作者、OSおよびハードウェアベンダー、その他の利害関係者からのフィードバックをGitHubを通じて歓迎する。 フィンガープリンティングに関する考慮事項の追加の議論については、§ 5 プライバシーの考慮事項を参照。

powerPreferenceオプションはMLPowerPreferenceであり、消費電力に関連するアプリケーションの 設定を示す。これは次のいずれかである。

"default"
ユーザーエージェントに最も適切な動作を選択させる。
"high-performance"
消費電力よりも実行速度を優先する。
"low-power"
実行速度などの他の考慮事項よりも消費電力を優先する。

acceleratedオプションは、大規模並列アクセラレーションに関連する アプリケーションの設定を示す。このオプションの優先度はpowerPreferenceよりも低い。 true(デフォルト)に設定されている場合、基盤プラットフォームは、powerPreferenceにも依存して、 GPUやNPUなど、利用可能な大規模並列アクセラレーターの使用を試みる。 falseに設定されている場合、アプリケーションはCPU推論を優先することを示す。例えばpowerPreference"high-performance"であり、 acceleratedfalseであるような矛盾する入力がある場合、実装は基盤プラットフォームで利用可能な最良の一致を選択する (例えば高性能CPUモード、またはacceleratedpowerPreferenceより優先度が低いため、それを無視する)。

8.2.2. createContext()

引数: 戻り値: MLContext
realm realmおよびoptionsGPUDevice またはMLContextOptions)が与えられたとき、 コンテキストを 作成するには、次の手順を実行する。
  1. contextを、realm内の新しいMLContextとする。

  2. optionsGPUDevice オブジェクトである場合:

    1. context.[[contextType]] を"webgpu"に設定する。

    2. context.[[powerPreference]]"default"に設定する。

    3. context.[[accelerated]]trueに設定する。

  3. それ以外の場合:

    1. context.[[contextType]] を"default"に設定する。

    2. context.[[lost]]realm内の新しいpromiseに設定する。

    3. options["powerPreference"] が存在する場合、context.[[powerPreference]]options["powerPreference"]に設定する。

    4. それ以外の場合、context.[[powerPreference]]"default"に設定する。

    5. options["accelerated"] が存在する場合、context.[[accelerated]]options["accelerated"]に設定する。

    6. それ以外の場合、context.[[accelerated]]trueに設定する。

  4. ユーザーエージェントがcontext.[[contextType]]を サポートできない場合、失敗を返す。

  5. contextを返す。

createContext(options)手順は次のとおりである。
  1. globalを、this関連グローバルオブジェクトとする。

  2. realmを、this関連realmとする。

  3. global関連Document使用を許可されていない webnn機能である場合、 "SecurityError" DOMExceptionrejectされた、 realm内の新しいpromiseを返す。

  4. promiserealm内の新しい promiseとする。

  5. 次の手順を並列に実行する。

    1. contextを、realmおよびoptionsが与えられてコンテキストを作成する結果とする。それが失敗を返す場合、globalとともに MLタスクをキューに入れpromiseを"NotSupportedError" DOMExceptionrejectし、 これらの手順を中止する。

    2. globalとともにMLタスクを キューに入れpromisecontext解決する。

  6. promiseを返す。

createContext(gpuDevice)メソッドの 手順は次のとおりである。
  1. globalを、this関連グローバルオブジェクトとする。

  2. realmを、this関連realmとする。

  3. global関連Document使用を許可されていない webnn機能である場合、 "SecurityError" DOMExceptionrejectされた、 realm内の新しいpromiseを返す。

  4. promiserealm内の新しい promiseとする。

  5. 次の手順を並列に実行する。

    1. contextを、realmおよびgpuDeviceが与えられてコンテキストを作成する結果とする。それが失敗を返す場合、globalとともに MLタスクをキューに入れpromiseを"NotSupportedError" DOMExceptionrejectし、 これらの手順を中止する。

    2. globalとともにMLタスクを キューに入れpromisecontext解決する。

  6. promiseを返す。

8.3. MLContext インターフェイス

MLContext インターフェイスは、ニューラルネットワーク計算ワークロードおよび実行プロセスのグローバル状態を表す。各MLContextオブジェクトは、 関連付けられたコンテキスト型およびMLPowerPreferenceを持つ。
typedef record<USVString, MLTensor> MLNamedTensors;

dictionary MLContextLostInfo {
  DOMString message;
};

[SecureContext, Exposed=(Window, Worker)]
interface MLContext {
  undefined dispatch(MLGraph graph, MLNamedTensors inputs, MLNamedTensors outputs);

  Promise<MLTensor> createTensor(MLTensorDescriptor descriptor);
  Promise<MLTensor> createConstantTensor(
    MLOperandDescriptor descriptor, AllowSharedBufferSource inputData);

  Promise<ArrayBuffer> readTensor(MLTensor tensor);
  Promise<undefined> readTensor(MLTensor tensor, AllowSharedBufferSource outputData);

  undefined writeTensor(MLTensor tensor, AllowSharedBufferSource inputData);

  MLOpSupportLimits opSupportLimits();

  undefined destroy();

  readonly attribute boolean accelerated;
  readonly attribute Promise<MLContextLostInfo> lost;
};
MLContext は次の内部スロットを持つ。
[[contextType]]、型はコンテキスト型

MLContextコンテキスト型

[[powerPreference]]、 型はMLPowerPreference

MLContextMLPowerPreference

[[accelerated]]、型はboolean

MLContextの 処理型(CPUまたは大規模並列処理)。

[[lost]]、型はPromise<MLContextLostInfo>。

PromiseMLContextの 基盤実行デバイスが利用できなくなったときに解決される。

[[timeline]]

MLContextの 計算ユニット上での演算の実行に関連付けられたタイムライン。 これらの演算には、計算グラフ上の推論、およびMLTensor[[data]] の変更が含まれる。

この タイムラインをより厳密に定義する。[Issue #529]

コンテキスト型は、 リソースを管理し、ニューラルネットワークグラフのコンパイルおよび実行を容易にする実行コンテキストの型である。

"default"
ユーザー設定オプションに従って作成されたコンテキスト。
"webgpu"
WebGPUデバイスから作成されたコンテキスト。
accelerated取得手順は、this.[[accelerated]]を返すことである。
AllowSharedBufferSource bufferSourceおよびMLOperandDescriptor descriptorが与えられたとき、記述子でバッファを検証するには、 次の手順を実行する。
  1. bufferSourceバイト長descriptorバイト長と等しくない場合、falseを返す。

  2. bufferSourceの型で分岐する。

    ArrayBuffer

    trueを返す。

    SharedArrayBuffer

    trueを返す。

    ArrayBufferView
    1. bufferSourceUint8Array オブジェクトである場合、trueを返す。

    2. bufferSourceが、この 表に従ってdescriptordataType と一致する場合、trueを返す。

    3. falseを返す。

注記: descriptordataType にかかわらずUint8Arrayを 使用することは、例えばWebAssembly.Memory インスタンスの一部など、ArrayBufferの スライスを表現する汎用的な方法としてサポートされる。開発者は、読みやすさと保守性のために、 WebNNコードを作成する際には、より具体的なビュー型を使用することが推奨される。

MLNamedTensors namedTensorsおよびrecord<USVString, MLOperandDescriptor> namedDescriptorsが与えられたとき、記述子でテンソルを検証するには:
  1. namedTensorsサイズnamedDescriptorsサイズと等しくない場合、 falseを返す。

  2. namedTensorsnametensorごとに反復する

    1. tensor.[[isConstant]] がtrueである場合、falseを返す。

    2. namedDescriptors[name]が存在しない場合、 falseを返す。

    3. tensor.[[descriptor]]namedDescriptors[name]と等しくない場合、falseを返す。

  3. trueを返す。

8.3.1. dispatch()

コンパイル済みMLGraphの計算ワークロードを、 MLContext[[timeline]]上にスケジュールする。

引数:

戻り値: undefined

注記: dispatch()自体は、 グラフ実行が完了したことを示すシグナルを提供しない。代わりに、呼び出し側は出力テンソルを読み戻した結果を awaitできる。下記の§ 8.3.1.1 例を参照。

dispatch(graph, inputs, outputs) メソッドの手順は次のとおりである。
  1. graph.[[context]]thisでない場合、TypeErrorthrowする。

  2. graph.[[isDestroyed]] がtrueである場合、"InvalidStateError" DOMExceptionthrowする。

  3. allTensorsを、inputsoutputs拡張したものからなる MLTensorリストとする。

  4. allTensorsに重複する項目が含まれる場合、 TypeErrorthrowする。

  5. allTensorsの各tensorについて反復する

    1. tensor.[[context]]thisでない場合、TypeErrorthrowする。

    2. tensor.[[isDestroyed]] がtrueである場合、TypeErrorthrowする。

  6. inputsおよびgraph.[[inputDescriptors]]が与えられて 記述子でテンソルを検証する結果がfalseを返す場合、 TypeErrorthrowする。

  7. outputsおよびgraph.[[outputDescriptors]]が与えられて 記述子でテンソルを検証する結果がfalseを返す場合、 TypeErrorthrowする。

  8. 次の手順をgraph.[[context]].[[timeline]]へ エンキューする。

    1. これらの手順を実行する。ただし、thislostであるときは中止する

      1. inputsおよびoutputsが与えられて、 graph.[[implementation]] に計算要求を発行する。

        グラフ実行中にエラーを報告する仕組みを追加する。 [Issue #778]

定数オペランドがテンソルを使用して作成される場合、buildの完了後にそのテンソルを破棄することは合法である。 実装は、コンパイル済みグラフがそのような破棄によって有効なままで影響を受けないことを保証することが期待される。

8.3.1.1.
次のコードは、MLGraphMLTensorを使用して実行する例を示す。
const descriptor = {
  dataType: 'float32',
  shape: [2, 2]
};
const context = await navigator.ml.createContext();
const builder = new MLGraphBuilder(context);

// 1. Create a computational graph 'C = 0.2 * A + B'.
const constant = builder.constant(descriptor, new Float32Array(4).fill(0.2));
const A = builder.input('A', descriptor);
const B = builder.input('B', descriptor);
const C = builder.add(builder.mul(A, constant), B);

// 2. Compile the graph.
const graph = await builder.build({'C': C});

// 3. Create reusable input and output tensors.
const [inputTensorA, inputTensorB, outputTensorC] = await Promise.all([
  context.createTensor({dataType: A.dataType, shape: A.shape, writable: true}),
  context.createTensor({dataType: B.dataType, shape: B.shape, writable: true}),
  context.createTensor({dataType: C.dataType, shape: C.shape, readable: true})
]);

// 4. Initialize the inputs.
context.writeTensor(inputTensorA, new Float32Array(4).fill(1.0));
context.writeTensor(inputTensorB, new Float32Array(4).fill(0.8));

// 5. Execute the graph.
const inputs = {
  'A': inputTensorA,
  'B': inputTensorB
};
const outputs = {
  'C': outputTensorC
};
context.dispatch(graph, inputs, outputs);

// 6. Read back the computed result.
const result = await context.readTensor(outputTensorC);
console.log('Output value:', new Float32Array(result));  // [1, 1, 1, 1]

8.3.2. createTensor()

このMLContextに関連付けられた MLTensorを作成する。

引数:

戻り値: Promise<MLTensor>。

createTensor(descriptor)メソッドの手順は 次のとおりである。
  1. globalを、this関連グローバルオブジェクトとする。

  2. realmを、this関連realmとする。

  3. thislostである場合、"InvalidStateError" DOMExceptionrejectされた、 realm内の新しい promiseを返す。

  4. tensorを、MLTensorを作成する結果とする。これはthisおよび descriptorが与えられる。

  5. promiserealm内の新しい promiseとする。

  6. 次の手順をthis.[[timeline]]へ エンキューする。

    1. これらの手順を実行する。ただし、thislostであるときは中止する

      1. descriptorが与えられて、tensor.[[data]] を作成し、すべてのバイトをゼロで初期化する。

      2. それが失敗した場合、globalとともにMLタスクをキューに入れpromiseを"UnknownError" DOMExceptionrejectし、 これらの手順を中止する。

      3. それ以外の場合、globalとともにMLタスクをキューに入れpromisetensor解決する。

    2. 中止された場合globalとともにMLタスクをキューに入れpromiseを"InvalidStateError" DOMExceptionrejectする。

  7. promiseを返す。

8.3.3. createConstantTensor()

このMLContextに関連付けられた定数MLTensorを作成する。

引数:

戻り値: Promise<MLTensor>。

createConstantTensor(descriptor, inputData) メソッドの手順は次のとおりである。
  1. globalを、this関連グローバルオブジェクトとする。

  2. realmを、this関連realmとする。

  3. thislostである場合、"InvalidStateError" DOMExceptionrejectされた、 realm内の新しい promiseを返す。

  4. descriptorが与えられて次元をチェックする結果がfalseを返す場合、 TypeErrorrejectされた、 realm内の新しい promiseを返す。

  5. inputDataおよびdescriptorが与えられて記述子でバッファを検証する結果がfalseを返す場合、 TypeErrorrejectされた、 realm内の新しいpromiseを返す。

  6. bytesを、inputDataが与えられてバッファソースが保持するバイトのコピーを取得する結果とする。

  7. Assert: bytes長さは、descriptorバイト長と等しい。

  8. tensorを、thisおよびdescriptorが与えられて定数MLTensorを作成する結果とする。

  9. promiserealm内の新しい promiseとする。

  10. 次の手順をthis.[[timeline]]へ エンキューする。

    1. これらの手順を実行する。ただし、thislostであるときは中止する

      1. descriptorが与えられて、tensor.[[data]] を作成する。

      2. それが失敗した場合、globalとともにMLタスクをキューに入れpromiseを"UnknownError" DOMExceptionrejectし、 これらの手順を中止する。

      3. bytestensor.[[data]]へコピーする。

      4. それが失敗した場合、globalとともにMLタスクをキューに入れpromiseを"UnknownError" DOMExceptionrejectし、 これらの手順を中止する。

      5. それ以外の場合、globalとともにMLタスクをキューに入れpromisetensor解決する。

    2. 中止された場合globalとともにMLタスクをキューに入れpromiseを"InvalidStateError" DOMExceptionrejectする。

  11. promiseを返す。

8.3.4. readTensor(tensor)

MLTensor[[data]]を、 MLContext.[[timeline]] からスクリプトへ読み戻す。

引数:

戻り値: Promise<ArrayBuffer>。 読み取り結果を含むバッファ。

readTensor(tensor)メソッドの手順は次のとおりである。
  1. globalを、this関連グローバルオブジェクトとする。

  2. realmを、this関連realmとする。

  3. tensor.[[context]]thisでない場合、TypeErrorrejectされた、 realm内の新しい promiseを返す。

  4. tensor.[[isDestroyed]] がtrueである場合、TypeErrorrejectされた、 realm内の新しい promiseを返す。

  5. tensor.[[descriptor]].readable がfalseである場合、TypeErrorrejectされた、 realm内の新しい promiseを返す。

  6. promiserealm内の新しい promiseとする。

  7. promisetensor.[[pendingPromises]]追加する。

  8. 次の手順をtensor.[[context]].[[timeline]]へ エンキューする。

    1. これらの手順を実行する。ただし、thislostであるときは中止する

      1. bytesを、tensor.[[data]]のコピーを含む バイト列とする。

      2. それが失敗した場合、globalと次の手順でMLタスクをキューに入れる

        1. tensor.[[pendingPromises]]から promise削除する。

        2. promiseを"UnknownError" DOMExceptionRejectし、 これらの手順を中止する。

      3. それ以外の場合、globalと次の手順でMLタスクをキューに入れる

        1. tensor.[[pendingPromises]]から promise削除する。

        2. bufferを、realm内でbytesからArrayBuffer作成する結果とする。

        3. promisebufferResolveする。

    2. 中止された場合globalとともにMLタスクをキューに入れpromiseを"InvalidStateError" DOMExceptionrejectする。

  9. promiseを返す。

8.3.5. readTensor(tensor, outputData)

readTensor(tensor)の bring-your-own-bufferバリアント。 [[data]] を、MLTensor から、提供されたバッファへ読み戻す。

引数:

戻り値: Promise<undefined>。

readTensor(tensor, outputData) メソッドの手順は次のとおりである。
  1. globalを、this関連グローバルオブジェクトとする。

  2. realmを、this関連realmとする。

  3. tensor.[[context]]thisでない場合、TypeErrorrejectされた、 realm内の新しい promiseを返す。

  4. tensor.[[isDestroyed]] がtrueである場合、TypeErrorrejectされた、 realm内の新しい promiseを返す。

  5. tensor.[[descriptor]].readable がfalseである場合、TypeErrorrejectされた、 realm内の新しい promiseを返す。

  6. outputDataおよびtensor.[[descriptor]] が与えられて記述子でバッファを検証する結果がfalseを返す場合、 TypeErrorrejectされた、 realm内の新しい promiseを返す。

  7. promiserealm内の新しい promiseとする。

  8. promisetensor.[[pendingPromises]]追加する。

  9. 次の手順をtensor.[[context]].[[timeline]]へ エンキューする。

    1. これらの手順を実行する。ただし、thislostであるときは中止する

      1. bytesを、tensor.[[data]]のコピーを含む バイト列とする。

      2. それが失敗した場合、次の手順を実行するため、globalとともにMLタスクをキューに入れる

        1. tensor.[[pendingPromises]]から promise削除する。

        2. promiseを"UnknownError" DOMExceptionRejectし、 これらの手順を中止する。

      3. それ以外の場合、次の手順を実行するため、globalとともにMLタスクをキューに入れる

        1. tensor.[[pendingPromises]]から promise削除する。

        2. outputDatadetachされている場合、 promiseTypeErrorrejectし、 これらの手順を中止する。

          注記: 上記の記述子でバッファを検証するは、 outputDataがdetachされている場合に失敗するが、その手順とこの手順の間に outputDataがdetachされる可能性がある。

        3. bytesoutputData書き込む

        4. promiseundefinedResolveする。

    2. 中止された場合globalとともにMLタスクをキューに入れpromiseを"InvalidStateError" DOMExceptionrejectする。

  10. promiseを返す。

8.3.6. writeTensor()

MLTensor[[data]] へ、MLContext[[timeline]]上でデータを書き込む。

引数:

戻り値: undefined

writeTensor(tensor, inputData) メソッドの手順は次のとおりである。
  1. tensor.[[context]]thisでない場合、TypeErrorthrowする。

  2. tensor.[[isDestroyed]] がtrueである場合、TypeErrorthrowする。

  3. tensor.[[descriptor]].writable がfalseである場合、TypeErrorthrowする。

  4. inputDataおよびtensor.[[descriptor]] が与えられて記述子でバッファを検証する結果がfalseを返す場合、 TypeErrorthrowする。

  5. bytesを、inputDataが与えられてバッファソースが保持するバイトのコピーを取得する結果とする。

  6. Assert: bytes長さは、tensor.[[descriptor]]バイト長と等しい。

  7. 次の手順をtensor.[[context]].[[timeline]]へ エンキューする。

    1. これらの手順を実行する。ただし、thislostであるときは中止する

      1. bytestensor.[[data]]へコピーする。

        テンソルへの書き込み中にエラーを報告する仕組みを追加する。 [Issue #778]

注記: dispatch()と同様に、 writeTensor()自体は、書き込みが完了したことを示すシグナルを提供しない。テンソルの内容を調べるために、 呼び出し側はテンソルを読み戻した結果をawaitできる。

8.3.7. opSupportLimits()

opSupportLimits()は、 実装間で演算子レベルにおいて異なるサポートレベルを公開する。WebNN APIの利用者は、 各ターゲットプラットフォームに配備する最適なモデルアーキテクチャを決定するために、opSupportLimits()を 使用して機能サポートレベルを調べることが推奨される。

注記: opSupportLimits() APIは、ブラウザーフィンガープリンティングのために追加のエントロピーを提供することを意図していない。現在の実装では、 この機能サポート情報はOSおよびブラウザーバージョンだけから推論できる。将来の実装の多様性がそれを正当化する場合、 このAPIにより、将来の実装は、エントロピーを低減するためWebGPUと同様に能力をバケット化するなど、 新しいプライバシー緩和策を追加できる。

フィンガープリンティングに関する考慮事項の追加の議論については、§ 5 プライバシーの考慮事項を参照。

8.3.7.1. MLOpSupportLimits 辞書
MLOpSupportLimitsは 次のトップレベルメンバーを持つ。これらに加えて、各演算子には、そのビルダーメソッドで定義される対応するメンバーがある。
dictionary MLOpSupportLimits {
  MLInputOperandLayout preferredInputLayout;
  [EnforceRange] unsigned long long maxTensorByteLength;
  MLTensorLimits input;
  MLTensorLimits constant;
  MLTensorLimits output;
};
preferredInputLayout, 型はMLInputOperandLayout

conv2d()など、 レイアウト依存演算子に対する推奨入力レイアウト。

maxTensorByteLength, 型はunsigned long long

テンソルのサポートされる最大長(バイト単位)。

input, 型はMLTensorLimits

MLGraphに対する 入力MLOperandのサポート制限。

constant, 型はMLTensorLimits

MLGraphに対する 定数MLOperandのサポート制限。

output, 型はMLTensorLimits

MLGraphに対する 出力MLOperandのサポート制限。

8.3.7.2. MLRankRange 辞書
dictionary MLRankRange {
  unsigned long min;
  unsigned long max;
};
min, 型はunsigned long

サポートされる最小ランク。

max, 型はunsigned long

サポートされる最大ランク。

8.3.7.3. MLTensorLimits 辞書
typedef sequence<MLOperandDataType> MLDataTypeList;

dictionary MLTensorLimits {
  MLDataTypeList dataTypes;
  MLRankRange rankRange;
};
dataTypes, 型はMLDataTypeList

サポートされるデータ型。

rankRange, 型はMLRankRange

サポートされる最小および最大ランク。

8.3.7.4. MLBinarySupportLimits 辞書
dictionary MLBinarySupportLimits {
  MLTensorLimits a;
  MLTensorLimits b;
  MLTensorLimits output;
};
a, 型はMLTensorLimits

aオペランド用のMLTensorLimits

b, 型はMLTensorLimits

bオペランド用のMLTensorLimits

output, 型はMLTensorLimits

出力オペランド用のMLTensorLimits

8.3.7.5. MLSingleInputSupportLimits 辞書
dictionary MLSingleInputSupportLimits {
  MLTensorLimits input;
  MLTensorLimits output;
};
input, 型はMLTensorLimits

入力オペランド用のMLTensorLimits

output, 型はMLTensorLimits

出力オペランド用のMLTensorLimits

8.3.8. destroy()

destroy() メソッドは、コンテキストに関連付けられたすべてのリソースを解放するために呼び出すことができる。未完了の計算要求、 およびMLTensorの 作成/読み取り/書き込み要求は失敗する。

destroy()メソッドの手順は次のとおりである。
  1. thislostである場合、これらの手順を中止する。

  2. 実装定義のメッセージで、thisloseする手順を実行する。

    注記: destroy()が呼び出されたことを示すメッセージは、開発者がコンテキスト喪失の原因を区別するのに役立つ。

8.3.9. エラー

ユーザーエージェントが、MLContextが 要求を満たすために利用できなくなったと判断した場合、そのためのコンテキスト喪失手順を実行しなければならない。

MLContext contextに対するコンテキスト喪失 手順は次のとおりである。
  1. globalを、context関連グローバルオブジェクトとする。

  2. 次の手順を実行するため、globalとともにMLタスクを キューに入れる

    1. Lose contextする。メッセージは実装定義とする。

MLContext contextを、DOMString messageloseするには:
  1. infoを新しいMLContextLostInfoとする。

  2. info.messagemessageに設定する。

  3. context.[[lost]]infoResolveする。

  4. graph.[[context]]thisと等しい各MLGraph graphについて:

    1. graphthisとして、 graphに対するdestroy() メソッド手順を実行する。

  5. tensor.[[context]]thisと等しい各MLTensor tensorについて:

    1. tensorthisとして、 tensorに対するdestroy() メソッド手順を実行する。

message, 型はDOMString

発生したエラーに関する情報を提供する実装定義のメッセージ。

lost取得手順は、this[[lost]] Promiseを返すことである。

MLContextは、 その[[lost]] Promisesettledしている場合、lostである

8.4. MLGraph インターフェイス

MLGraph インターフェイスは、コンパイル済み計算グラフを表す。コンパイル済みグラフは、一度構築されると不変であり、 その後変更できない。
[SecureContext, Exposed=(Window, Worker)]
interface MLGraph {
  undefined destroy();
};
MLGraphは 次の内部スロットを持つ。
[[context]]、型はMLContext

このMLGraphに関連付けられた MLContext型のコンテキスト。

[[inputDescriptors]]、型は record<USVString, MLOperandDescriptor>

このMLGraphのすべての 入力MLOperandについて、 入力MLOperandの名前を そのMLOperandDescriptorに対応付ける。

[[outputDescriptors]]、型は record<USVString, MLOperandDescriptor>

このMLGraphのすべての 出力MLOperandについて、 出力MLOperandの名前を そのMLOperandDescriptorに対応付ける。

[[implementation]]

ユーザーエージェントにより提供される基盤実装。

[[isDestroyed]]、型はboolean

MLGraph.destroy() メソッド手順が実行されたかどうか。いったん破棄されると、MLGraph はもはや使用できない。

8.4.1. destroy()

destroy() メソッドは、グラフに関連付けられたすべてのリソースを解放するために呼び出すことができる。

destroy()メソッドの手順は次のとおりである。
  1. this.[[isDestroyed]] がtrueである場合、これらの手順を中止する。

  2. this.[[isDestroyed]] をtrueに設定する。

  3. このグラフが所有するリソースを解放可能としてマークするために、this.[[context]].[[timeline]] 上にタスクをキューに入れる。

注記: このグラフを使用してこれ以上ワークロードをキューに入れることはできないため、 実装は、このグラフを使用して以前に送信されたすべてのワークロードが完了した後、このグラフに関連付けられた追加のリソース割り当てを解放できる。

8.5. MLOperandDescriptor 辞書

MLOperandDescriptorは、 オペランドの形状(次元)およびデータ型を記述する。これはMLGraphの入力および 定数を記述するために使用され、各MLOperandは 内部MLOperandDescriptorを持つ。

enum MLInputOperandLayout {
  "nchw",
  "nhwc"
};

enum MLOperandDataType {
  "float32",
  "float16",
  "int32",
  "uint32",
  "int64",
  "uint64",
  "int8",
  "uint8"
};

dictionary MLOperandDescriptor {
  required MLOperandDataType dataType;
  required sequence<[EnforceRange] unsigned long> shape;
};
dataType, 型はMLOperandDataType

オペランドのデータ型。

shape, 型はsequence<[EnforceRange] unsigned long>

オペランドの次元のリスト。スカラーオペランドの場合は空である。

MLOperandDescriptor Aは、A.dataTypeB.dataTypeと等しく、 かつA.shapeB.shape等しい場合、MLOperandDescriptor B等しい
MLOperandDataType dataTypeおよびリストshapeが与えられたとき、MLOperandDescriptorを 作成するには、次の手順を実行する。
  1. descriptorを新しいMLOperandDescriptorとする。

  2. descriptor.dataTypedataTypeに設定する。

  3. descriptor.shapeshapeクローンに設定する。

  4. descriptorを返す。

MLOperandDescriptor descバイト長は、次の手順により返される値である。
  1. elementLengthを1とする。

  2. desc.shapeの 各dimensionについて反復する

    1. elementLengthelementLength * dimensionに設定する。

  3. elementSizeを、この 表に従ってdesc.dataTypeと 一致するArrayBufferView 型の1つの要素サイズとする。

  4. elementLength * elementSizeを返す。

MLOperandDescriptor desc要素数は、次の手順により返される値である。
  1. elementCountを1とする。

  2. desc.shapeの 各dimensionについて反復する

    1. elementCountelementCount * dimensionに設定する。

  3. elementCountを返す。

妥当な次元は、 0より大きく、longの範囲内にある整数である。 実装はより小さな上限を課してもよい。

妥当なテンソル 数は、0より大きく8192以下の整数である。実装はより小さな上限を課してもよい。

サイズ0の次元は サポートされるべきか? [Issue #391]

MLOperandDescriptor descriptorが与えられたとき、次元をチェックするには、次の手順を実行する。
  1. descriptor.shapeの いずれかの項目妥当な 次元でない場合、falseを返す。

  2. descriptor.shapeサイズが実装でサポートするには大きすぎる場合、 falseを返す。

    オペランド次元の最大数は 定義されていないが、ネイティブML APIは通常、サポートされる最大サイズを持つ。[Issue #456]

  3. descriptor要素数妥当な 次元でない場合、falseを返す。

  4. descriptorバイト長が実装でサポートされていない場合、 falseを返す。

  5. trueを返す。

8.6. MLOperand インターフェイス

MLOperandは、 演算の一部を完全に合成された演算へ合成した結果として構築される、中間グラフを表す。

例えば、MLOperandは、 演算に供給される定数、または複数の定数を1つの演算へ結合した結果を表すことができる。 § 7 プログラミングモデルも参照。

[SecureContext, Exposed=(Window, Worker)]
interface MLOperand {
  readonly attribute MLOperandDataType dataType;
  readonly attribute FrozenArray<unsigned long> shape;
};

dictionary MLOperatorOptions {
  USVString label = "";
};

typedef (bigint or unrestricted double) MLNumber;
MLOperand は次の内部スロットを持つ。
[[builder]]、型はMLGraphBuilder

MLOperandの 関連ビルダーオブジェクト。

[[descriptor]]、型はMLOperandDescriptor

MLOperandの 記述子。

[[name]]、型は文字列

MLOperandの 名前(入力オペランドの場合のみ)。

[[operator]]、型は演算子

MLOperandに 対応する演算子への参照。

[[constantTensor]]、型は MLTensor

MLOperandの テンソル(定数オペランドの場合のみ)。

MLOperanddataTypeは、その[[descriptor]].dataTypeである。

MLOperandshapeは、その[[descriptor]].shapeである。

MLOperandrankは、そのshapeサイズである。

dataType取得手順は、 thisdataTypeを返すことである。

shape取得手順は、 thisshapeを返すことである。

[[builder]] オブジェクトは、MLGraphBuilder() コンストラクターによりMLContext オブジェクトに束縛されるため、MLOperandも 常に同じMLContext オブジェクトに束縛される。

演算がMLOperandDataTypeの サブセットのみをサポートする場合、位置引数とオプションの両方を含む、演算の各入力オペランドに対する許可されるデータ 型は、MLOperandDataTypeの 明示的なリスト、またはオペランドのdataTypeが別の入力オペランドのdataType同じでなければならないという制約、または任意のMLOperandDataTypeを 許可する任意として与えられる。

実装は、指定されているより少ないデータ型をオペランドに対してサポートしてもよい。これは、 MLContext上のopSupportLimits() メソッドを使用し、演算に対応するメンバーのdataTypes 値を調べることにより、各演算について照会できる。

各演算子に対して サポートされなければならないデータ型のサブセットを指定すべきか?

演算が特定のrankを持つ入力オペランドを必要とする場合、位置引数とオプションの両方を含む、 演算の各入力オペランドに対する許可されるランクは、明示的なランク(例: 1)、または任意の次元数を許可するN、または別のオペランドと 同じとして与えられる。より具体的な制約も一般的であり、例えば入力オペランドの形状が 別の入力オペランドに対して単方向にブロードキャスト可能でなければならない場合、または双方向にブロードキャスト可能でなければならない場合がある。 これらの場合、許可される ランクは範囲として列挙され、具体的な検証は演算内の手順として与えられる。

実装は、オペランドのrankに対して、指定されているより制限された下限および/または上限を課してもよい。 これは、MLContext上のopSupportLimits() メソッドを使用し、演算に対応するメンバーのrankRange.min およびrankRange.max 値を調べることにより、各演算について照会できる。

MLOperatorOptions は次のメンバーを持つ。

label, 型はUSVString、デフォルトは""

MLOperandを作成する MLGraphBuilder メソッドを使用して演算子が作成されるときに任意で提供される。 実装はこの値を使用して演算子ラベルを初期化してもよい。

注記: ラベルは自然言語文字列であることを意図していない。 これは、"mul#1234"のような、変数名またはエラーコードに類似した言語非依存の識別子である。

注記: 実装は、開発者から提供されたlabelを 使用して、グラフ構築中の同期エラー、および非同期build() メソッド中に発生するエラーの両方を含め、エラーメッセージを強化しデバッグ容易性を向上させることが推奨される。

デバッグツール、ログ、またはエラーメッセージで、開発者がlabel を通じて提供したラベルを表示するとき、実装は出力をサニタイズして、悪意あるUnicodeシーケンスの注入などの セキュリティリスクを防止すべきである(例: 双方向テキスト スプーフィング [UTR36]ソースコードスプーフィング [UTS55]および その他の懸念)。例えば、実装は制御文字(例: U+202A からU+202E、U+2066からU+2069)をエスケープまたはフィルタリングするか、安全なレンダリング機構を使用して潜在的な スプーフィングを無効化すべきである。

8.6.1. MLOperandの作成

MLOperand オブジェクトは、MLGraphBuilderの メソッドにより、内部的に次のアルゴリズムを使用して作成される。
MLGraphBuilder builderおよびMLOperandDescriptor descが与えられたとき、MLOperandを 作成するには、次の手順を実行する。
  1. realmを、builder関連realmとする。

  2. operandrealm内の新しいMLOperand とする。

  3. operand.[[builder]]builderに設定する。

  4. operand.[[descriptor]]descに設定する。

  5. operandを返す。

MLOperand operandが与えられたとき、MLOperandを コピーするには、次の手順を実行する。
  1. builderoperand.[[builder]]とする。

  2. realmを、builder関連realmとする。

  3. resultrealm内の新しいMLOperand とする。

  4. result.[[builder]]builderに設定する。

  5. result.[[descriptor]]operand.[[descriptor]]に設定する。

  6. operand.[[name]]存在する場合、result.[[name]]operand.[[name]]に設定する。

  7. resultを返す。

MLGraphBuilder builderおよびMLOperand operandが与えられたとき、オペランドを検証するには、operand.[[builder]]builderであればtrueを返し、そうでなければfalseを返す。

8.6.1.1. MLNumber

MLNumberは、64ビット整数型("uint64" および"int64")と 32ビット浮動小数点("float32")の 両方を含む、任意のMLOperandDataTypeであり得る MLOperandに対する数値オプションの型を指定するときに使用される。 実装は、対応するMLOperandDataTypeに従って値を処理する。 例えば、clamp(input, options)が、 dataType"uint32"である MLOperandで呼び出された場合、 MLNumber パラメーターは明示的にunsigned longキャストされる。

オプションをdoubleとして指定すると、 253を超える値を渡すときに精度が失われ、long longを 指定すると263を超える値が許可されなくなる。

bigint数値型のunionのサポートは[WEBIDL]で新しく、実装サポートも限定的である。 プロトタイプ実装には、このアプローチについてフィードバックを提供することが推奨される。[whatwg/webidl Issue #1388]

8.7. MLTensorDescriptor 辞書

MLTensorDescriptorは、 MLTensorの特性および能力を記述する。

dictionary MLTensorDescriptor : MLOperandDescriptor {
  boolean readable = false;
  boolean writable = false;
};
readable, 型はboolean、デフォルトはfalse

テンソルの内容をreadTensor(tensor) またはreadTensor(tensor, outputData)を通じて読み取れるかどうか。

writable, 型はboolean、デフォルトはfalse

テンソルの内容をwriteTensor()を通じて書き込めるかどうか。

8.8. MLTensor インターフェイス

MLTensor インターフェイスは、MLGraphへの入力または出力として使用できるテンソルを表す。MLTensorを裏付けるメモリは、 それを作成するために使用されたMLContextおよび MLTensorDescriptorの要件に従って、 実装定義の方法で割り当てられるべきである。MLTensor[[data]] に関わる演算は、関連するMLContext[[timeline]] 上で発生する。

MLTensorがどのように割り当てられるかについての 実装定義の要件には、メモリが特定のバイトアラインメントで割り当てられる、 または特定のメモリプール内で割り当てられるといった制約が含まれ得る。

[SecureContext, Exposed=(Window, Worker)]
interface MLTensor {
  readonly attribute MLOperandDataType dataType;
  readonly attribute FrozenArray<unsigned long> shape;
  readonly attribute boolean readable;
  readonly attribute boolean writable;
  readonly attribute boolean constant;

  undefined destroy();
};
MLTensorは 次の内部スロットを持つ。
[[context]]、型はMLContext

MLTensorの 関連コンテキスト。

[[descriptor]]、型はMLTensorDescriptor

MLTensorの 記述子。

[[pendingPromises]]、型は Promise集合

進行中でまだ解決されていないMLContext.readTensor(tensor) メソッド呼び出しに対応するPromise。MLTensor が破棄されると、すべての保留中のpromiseはrejectされる。

[[isDestroyed]]、型はboolean

MLTensor.destroy() 手順が実行されたかどうか。いったん破棄されると、MLTensor はもはや使用できない。

[[data]]、型は実装定義の型

MLTensorを 裏付けるバイト。このデータは[[context]].[[timeline]] からのみアクセスまたは変更できる。

[[isConstant]]、型はboolean

MLTensor定数MLTensorを作成するにより作成されたかどうか。

MLTensordataTypeは、その[[descriptor]]dataTypeである。

MLTensorshapeは、その[[descriptor]]shapeである。

dataType取得手順は、 thisdataTypeを返すことである。

shape取得手順は、 thisshapeを返すことである。

readable取得手順は、 this.[[descriptor]].readableを返すことである。

writable取得手順は、 this.[[descriptor]].writableを返すことである。

constant取得手順は、 this[[isConstant]]を返すことである。

8.8.1. MLTensorの作成

MLTensorは、 関連付けられたMLContextにより作成される。

MLContext contextおよびMLTensorDescriptor descriptorが与えられたとき、MLTensorを 作成するには、次の手順を実行する。
  1. realmを、context関連realmとする。

  2. tensorrealm内の新しいMLTensor とする。

  3. tensor.[[context]]contextに設定する。

  4. tensor.[[descriptor]]descriptorに設定する。

  5. tensor.[[isDestroyed]] をfalseに設定する。

  6. tensor.[[isConstant]] をfalseに設定する。

  7. tensorを返す。

8.8.2. destroy()

MLTensorに関連付けられたリソースを解放する。この メソッドは冪等である。

戻り値: undefined
destroy()メソッドの手順は次のとおりである。
  1. this.[[isDestroyed]] をtrueに設定する。

  2. promiseについて、this.[[pendingPromises]]内で:

    1. this.[[pendingPromises]]から promise削除する。

    2. promiseを"InvalidStateError" DOMExceptionRejectする。

  3. 次の手順をthis.[[context]].[[timeline]]へ エンキューする。

    1. this.[[data]]を解放する。

注記: このテンソルを使用してこれ以上演算をキューに入れることはできないため、 実装は、このテンソルを使用して以前に送信されたすべての演算が完了した後、このテンソルに関連付けられた追加のリソース割り当てを解放できる。

8.8.3. 定数MLTensorの作成

定数MLTensorは、 関連付けられたMLContextにより作成される。

MLContext contextMLOperandDescriptor inputDescriptorが与えられたとき、定数MLTensorを 作成するには、次の手順を実行する。
  1. realmを、context関連realmとする。

  2. tensorrealm内の新しいMLTensor とする。

  3. tensor.[[context]]contextに設定する。

  4. tensorDescriptorを新しいMLTensorDescriptorとする。

  5. tensorDescriptor.readable をfalseに設定する。

  6. tensorDescriptor.writable をfalseに設定する。

  7. tensorDescriptor.dataTypeinputDescriptor.dataTypeに設定する。

  8. tensorDescriptor.shapeinputDescriptor.shapeに設定する。

  9. tensor.[[descriptor]]tensorDescriptorに設定する。

  10. tensor.[[isDestroyed]] をfalseに設定する。

  11. tensor.[[isConstant]] をtrueに設定する。

  12. tensorを返す。

8.9. MLGraphBuilder インターフェイス

MLGraphBuilder インターフェイスは、§ 2 ユースケースで特定される、計算グラフへ合成できる一連の演算を定義する。 また、グラフ構築セッションの中間状態も表す。

typedef record<USVString, MLOperand> MLNamedOperands;

[SecureContext, Exposed=(Window, Worker)]
interface MLGraphBuilder {
  // Construct the graph builder from the context.
  constructor(MLContext context);

  // Create an operand for a graph input.
  MLOperand input(USVString name, MLOperandDescriptor descriptor);

  // Create an operand for a graph constant.
  MLOperand constant(MLOperandDescriptor descriptor,
                     AllowSharedBufferSource buffer);

  // Create a scalar operand from the specified number of the specified type.
  MLOperand constant(MLOperandDataType dataType, MLNumber value);

  // Create an operand from a specified constant tensor.
  MLOperand constant(MLTensor tensor);

  // Compile the graph up to the specified output operands asynchronously.
  Promise<MLGraph> build(MLNamedOperands outputs);
};
MLGraphBuilder.build() メソッドは、グラフビルダー状態を、指定された出力オペランドまで、作成元のMLContextの型に従って コンパイル済みグラフへコンパイルする。MLContext[[contextType]] が"default"に設定されている場合、コンパイル済みグラフは MLGraphが 返される直前に初期化される。このグラフ初期化段階は、後続のグラフ実行の最適な性能にとって重要である。 通常これは"weight preprocessing"として知られるプロセスを伴い、グラフへのすべての定数入力が前処理され、 後続のグラフ実行呼び出しのためにオペレーティングシステムレベルでキャッシュされる。 初期化入力は通常、グラフ構築時にconstant() メソッドを通じて定数オペランドとして指定された定数重みデータである。
MLGraphBuilder は次の内部スロットを持つ。
[[context]]、型はMLContext

このMLGraphBuilderに関連付けられた MLContext型のコンテキスト。

[[hasBuilt]]、型はboolean

MLGraphBuilder.build() が呼び出されたかどうか。いったん構築されると、MLGraphBuilder はもはや演算子を作成したり、MLGraphをコンパイルしたりできない。

MLGraphBuilderは、 その[[hasBuilt]] がfalseであり、かつその[[context]]lostでない場合、 buildできる

8.9.1. MLGraphBuilder コンストラクター

引数:
new MLGraphBuilder(context) コンストラクターの手順は次のとおりである。
  1. this関連グローバルオブジェクト関連Documentwebnn機能の使用を許可されていない場合、"SecurityError" DOMExceptionthrowする。

  2. contextlostである場合、"InvalidStateError" DOMExceptionthrowする。

  3. this.[[context]]contextに設定する。

  4. this.[[hasBuilt]] をfalseに設定する。

8.9.2. 入力オペランド

入力として使用できる、記述子に基づく名前付きMLOperandを作成する。

引数: 戻り値: MLOperand
input(name, descriptor) メソッドの手順は次のとおりである。
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. nameが空である場合、TypeErrorthrowする。

  3. thisグラフ入力内のいずれかの MLOperandが、 nameと等しい[[name]]を 持つ場合、TypeErrorthrowする。

  4. descriptorが与えられて次元をチェックする結果がfalseを返す場合、 TypeErrorthrowする。

  5. グラフ接続を作成する:

    1. operandを、thisおよび descriptorが与えられてMLOperandを 作成する結果とする。

    2. operand.[[name]]nameに設定する。

    3. operandthisグラフ入力へ追加する。

  6. operandを返す。

MLGraphBuilder APIは、入力オペランドなしでMLGraphを作成することを許可する。 基盤プラットフォームがそれをサポートしていない場合、実装はスタブ入力を追加するか、定数をグラフへの入力として渡すことができる。

8.9.3. 定数オペランド

MLGraphBuilder メソッドで使用できる定数MLOperandを作成する。
8.9.3.1. constant(descriptor, buffer)
初期化データを含む、指定されたデータ型および形状の定数MLOperandを作成する。
引数: 戻り値: MLOperand。 定数出力テンソル。
constant(descriptor, buffer) メソッドの手順は次のとおりである。
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. descriptorが与えられて次元をチェックする結果がfalseを返す場合、 TypeErrorthrowする。

  3. bufferおよびdescriptorが与えられて記述子でバッファを検証する結果がfalseを返す場合、 TypeErrorthrowする。

  4. グラフ接続を作成する:

    1. operandを、thisおよび descriptorが与えられてMLOperandを 作成する結果とする。

    2. bytesを、bufferが与えられてバッファソースが保持するバイトのコピーを取得する結果とする。

    3. operandを、bytesを値としてthisグラフ定数へ追加する。

  5. operandを返す。

8.9.3.2. constant(tensor)
初期化済みデータを含む、指定されたデータ型および形状の定数MLOperandを作成する。
引数: 戻り値: MLOperand。 定数出力テンソル。
constant(tensor)メソッドの手順は 次のとおりである。
  1. tensor.[[context]]this.[[context]]でない場合、 TypeErrorthrowする。

  2. tensor.[[isDestroyed]] がtrueである場合、TypeErrorthrowする。

  3. tensor.[[isConstant]] がfalseである場合、TypeErrorthrowする。

  4. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  5. グラフ接続を作成する:

    1. operandを、thisおよび tensor.[[descriptor]]が 与えられてMLOperandを 作成する結果とする。

    2. operand.[[constantTensor]]tensorに設定する。

    3. operandを、tensorを値としてthisグラフ定数へ追加する。

  6. operandを返す。

8.9.3.3. constant(dataType, value)
指定された値およびデータ型のスカラー定数MLOperandを作成する。
指定された値が指定された出力データ型の範囲を超える場合、例えば浮動小数点値が"int8" データ型に割り当てられる場合などには、データの切り捨てが発生する。
引数: 戻り値: MLOperand。 定数出力。
constant(dataType, value) メソッドの手順は次のとおりである。
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. valueを、valuedataTypeキャストする結果に設定する。

  3. descriptorを、dataTypeおよび« »が与えられてMLOperandDescriptorを 作成する結果とする。

  4. グラフ接続を作成する:

    1. operandを、thisおよび descriptorが与えられてMLOperandを 作成する結果とする。

    2. operandを、valueを値としてthisグラフ定数へ追加する。

  5. operandを返す。

8.9.4. buildメソッド

与えられた出力オペランドまでの合成済みグラフを、非同期に計算グラフへ構築する。
引数: 戻り値: Promise<MLGraph>。
build(outputs)メソッドの手順は次のとおりである。
  1. realmを、this関連realmとする。

  2. thisbuildできない場合、"InvalidStateError" DOMExceptionrejectされた、 realm内の新しいpromiseを返す。

  3. outputsが空である場合、TypeErrorrejectされた、 realm内の新しい promiseを返す。

  4. outputsの各nameoperandについて反復する

    1. nameが空である場合、TypeErrorrejectされた、 realm内の新しい promiseを返す。

    2. thisおよびoperandが与えられてオペランドを検証する結果がfalseを返す場合、TypeErrorrejectされた、realm内の新しいpromiseを返す。

    3. operandthisグラフ入力 または定数内にある場合、TypeErrorrejectされた、realm内の新しいpromiseを返す。

    4. operand.[[constantTensor]] が存在し、かつoperand.[[constantTensor]].[[isDestroyed]] がtrueである場合、TypeErrorrejectされた、 realm内の新しい promiseを返す。

  5. operandsを新しい空の集合とする。

  6. operatorsを新しい空の集合とする。

  7. inputsを新しい空の集合とする。

  8. queueを、outputsを含む新しいキューとする。

  9. queue空で ない間:

    1. queueからoperandデキューする。

    2. operandoperands追加する。

    3. operand.[[operator]]operators追加する。

    4. operandthisグラフ入力内にある場合、operandinputs追加する。

    5. operand.[[operator]]入力の 各inputについて反復する

      1. inputqueueエンキューする。

  10. globalを、this関連グローバルオブジェクトとする。

  11. graphrealm内の新しいMLGraph とする。

  12. graph.[[context]]this.[[context]]に設定する。

  13. graph.[[isDestroyed]] をfalseに設定する。

  14. inputs内の各operandについて反復する

    1. graph.[[inputDescriptors]][operand.[[name]]] をoperand.[[descriptor]]に設定する。

  15. outputsの各nameoperandについて反復する

    1. graph.[[outputDescriptors]][name] をoperand.[[descriptor]]に設定する。

  16. this.[[hasBuilt]] をtrueに設定する。

  17. promiserealm内の新しい promiseとする。

  18. 次の手順をgraph.[[context]].[[timeline]]へ エンキューする。

    1. これらの手順を実行する。ただし、graph.[[context]]lostであるときは中止する

      1. graphImplを、thisグラフを、operandsoperatorsinputs、およびoutputs、さらに graph.[[context]].[[powerPreference]] およびgraph.[[context]].[[accelerated]] とともに、基盤プラットフォームにより解釈できる実装定義の形式へ変換した結果とする。

      2. 前の手順が失敗した場合、globalとともにMLタスクを キューに入れpromiseを"OperationError" DOMExceptionrejectし、 これらの手順を中止する。

      3. graph.[[implementation]]graphImplに設定する。

      4. globalとともにMLタスクをキューに入れpromisegraphresolveする。

    2. 中止された場合globalとともにMLタスクをキューに入れpromiseを"InvalidStateError" DOMExceptionrejectする。

  19. promiseを返す。

注記: 入力オペランドまたは定数オペランドをグラフの出力として指定すると、 これは通常APIの不正な使用であるため、エラーになる。呼び出し側はidentity() 演算子を導入することでこれを回避できる。

8.9.5. argMin/argMax演算

軸に沿ったすべての入力値の最小値または最大値のインデックス位置を返す。同値の場合、 返り値の同一性は実装依存である。
dictionary MLArgMinMaxOptions : MLOperatorOptions {
  boolean keepDimensions = false;
  MLOperandDataType outputDataType = "int32";
};

partial interface MLGraphBuilder {
  MLOperand argMin(MLOperand input, [EnforceRange] unsigned long axis,
                   optional MLArgMinMaxOptions options = {});
  MLOperand argMax(MLOperand input, [EnforceRange] unsigned long axis,
                   optional MLArgMinMaxOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits argMin;
  MLSingleInputSupportLimits argMax;
};

MLArgMinMaxOptions は次のメンバーを持つ。

keepDimensions, 型は boolean、デフォルトはfalse

trueの場合、縮約された次元をサイズ1で保持する。

outputDataType, 型は MLOperandDataType、デフォルトは "int32"

MLOperandDataType。 出力データ型。

引数:

戻り値: MLOperandkeepDimensions がtrueの場合はinputrankと等しいrankkeepDimensions がfalseの場合はinputrank - 1である出力N次元テンソル。 値は、Nがaxisにより指定される入力次元のサイズであるとき、 [0, N-1]の範囲内のoutputDataType 型でなければならない。

argMin()/argMax()のテンソル制限
オペランド 許可されるデータ 型 許可されるランク
input 任意 1からN
output "int32", "int64" N

MLOpSupportLimitsargMin() およびargMax()について次のメンバーを持つ。

argMin, 型はMLSingleInputSupportLimits

argMin()演算子のサポート制限。

argMax, 型はMLSingleInputSupportLimits

argMax()演算子のサポート制限。

文字列 opMLOperand inputunsigned long axis、およびMLArgMinMaxOptions optionsが与えられたとき、argMin/argMax演算を作成するには、次の手順を実行する。
  1. Assert: opは"argMin", "argMax"のいずれかである。

  2. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  3. thisおよびinputとともにオペランドを検証する結果がfalseを返す場合、TypeErrorthrowする。

  4. axisinputrank以上である場合、TypeErrorthrowする。

  5. options.outputDataType が(この表に従う)出力テンソルの許可されるデータ型でない場合、TypeErrorthrowする。

  6. inputshape[axis]が options.outputDataTypeの 最大値より大きい場合、TypeErrorthrowする。

  7. outputShapeを、inputshape、« axis »、およびoptions.keepDimensions が与えられて縮約出力サイズを計算する結果とする。 それが失敗を返す場合、TypeErrorthrowする。

  8. descを、options.outputDataType およびoutputShapeが与えられてMLOperandDescriptorを 作成する結果とする。

  9. グラフ接続を作成する:

    1. operatorを、optionsが与えられた、op演算用の演算子とする。

    2. outputを、thisおよび descが与えられてMLOperandを 作成する結果とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. operatoroutputoutputに設定する。

  10. outputを返す。

次のargMin/argMaxアルゴリズムがサポートされる。
argMin(input, axis, options) メソッドの手順は次のとおりである。
  1. outputを、"argMin"、inputaxis、および optionsが与えられてargMin/argMax演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

argMax(input, axis, options) メソッドの手順は次のとおりである。
  1. outputを、"argMax"、inputaxis、および optionsが与えられてargMin/argMax演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

8.9.6. batchNormalization

[Batch-Normalization]を用いて入力テンソルの値を正規化する。 入力特徴量ごとに、モデルの訓練中に、その特徴量の平均値および分散値がバッチ次元内のすべてのサンプルにわたって計算される。 これらの平均値および分散値は、その後、モデル推論時にこの演算へ与えられる。
dictionary MLBatchNormalizationOptions : MLOperatorOptions {
  MLOperand scale;
  MLOperand bias;
  [EnforceRange] unsigned long axis = 1;
  double epsilon = 1e-5;
};

partial interface MLGraphBuilder {
  MLOperand batchNormalization(MLOperand input, MLOperand mean, MLOperand variance,
                               optional MLBatchNormalizationOptions options = {});
};

dictionary MLBatchNormalizationSupportLimits {
  MLTensorLimits input;
  MLTensorLimits mean;
  MLTensorLimits variance;
  MLTensorLimits scale;
  MLTensorLimits bias;
  MLTensorLimits output;
};

partial dictionary MLOpSupportLimits {
  MLBatchNormalizationSupportLimits batchNormalization;
};

MLBatchNormalizationOptions は次のメンバーを持つ。

scale, 型はMLOperand

スケーリング値の1次元テンソルであり、そのサイズは、axisにより示される入力次元のサイズに等しい。

bias, 型はMLOperand

バイアス値の1次元テンソルであり、そのサイズは、axisにより示される入力次元のサイズに等しい。

axis, 型はunsigned long、デフォルトは1

平均値および分散値が対応する、入力形状の特徴量数次元へのインデックス。 その値は、Nが入力テンソルのrankであるとき、[0, N-1]の範囲内でなければならない。 デフォルト値は1であり、"nchw" データレイアウトにおけるチャンネル("c")次元に対応する。

epsilon, 型はdouble、デフォルトは1e-5

ゼロ除算による計算エラーを防ぐための小さい値。

引数:

戻り値: MLOperandinputと同じ形状を持つ、バッチ正規化済みN次元テンソル。

batchNormalization()のテンソル制限
オペランド 許可されるデータ 型 許可されるランク
input "float32", "float16" 1からN
mean input同じ 1
variance input同じ 1
scale input同じ 1
bias input同じ 1
output input同じ input同じ

MLBatchNormalizationSupportLimits は次のメンバーを持つ。

input, 型はMLTensorLimits

入力オペランド用のMLTensorLimits

mean, 型はMLTensorLimits

meanオペランド用のMLTensorLimits

variance, 型はMLTensorLimits

varianceオペランド用のMLTensorLimits

scale, 型はMLTensorLimits

scaleオペランド用のMLTensorLimits

bias, 型はMLTensorLimits

biasオペランド用のMLTensorLimits

output, 型はMLTensorLimits

出力オペランド用のMLTensorLimits

MLOpSupportLimitsbatchNormalization()について次のメンバーを持つ。

batchNormalization, 型はMLBatchNormalizationSupportLimits

batchNormalization()演算子のサポート制限。

batchNormalization(input, mean, variance, options) メソッドの手順は次のとおりである。
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することを、thisおよびinputmeanvarianceoptions.scale (それが存在する場合)、およびoptions.bias (それが存在する場合)のいずれかとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. inputdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

  4. options.axis が0以上inputrank未満の範囲内にない場合、TypeErrorthrowする。

  5. meandataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

  6. meanshapeが、« inputshape[options.axis] » と等しくない場合、TypeErrorthrowする。

  7. variancedataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

  8. varianceshapeが、« inputshape[options.axis] » と等しくない場合、TypeErrorthrowする。

  9. options.epsilon を、options.epsiloninputdataTypeキャストする結果に設定する。

  10. options.scale存在する場合:

    1. そのdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

    2. そのshapeが、« inputshape[options.axis] » と等しくない場合、TypeErrorthrowする。

  11. options.bias存在する場合:

    1. そのdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

    2. そのshapeが、« inputshape[options.axis] » と等しくない場合、TypeErrorthrowする。

  12. グラフ接続を作成する:

    1. operatorを、inputmeanvarianceおよび optionsが与えられた、"batchNormalization"演算用の演算子とする。

    2. outputを、thisおよび input.[[descriptor]]が与えられてMLOperandを 作成する結果とする。

    3. output.[[operator]]operatorに設定する。

    4. operator入力inputmean、および varianceに設定する。

    5. options.scale存在する場合、それをoperator入力へ追加する。

    6. options.bias存在する場合、それをoperator入力へ追加する。

    7. operatoroutputoutputに設定する。

  13. outputを返す。

入力テンソルが"nchw" レイアウトの4次元である場合のこの演算の動作は、次のように他の演算の使用から汎用的にエミュレートできる。 ただし、ユーザーエージェントは通常、より効率的な実装を持つ。 基盤プラットフォームがある演算を直接サポートしない場合、この分解は実装を導くテンプレートとして使用できる。
function batchNormalization(builder, input, mean, variance, options) {
  const shape = [1, input.shape[options.axis], 1, 1];
  return builder.add(
    builder.mul(
      builder.reshape(options.scale, shape),
      builder.div(
        builder.sub(input, builder.reshape(mean, shape)),
        builder.sqrt(builder.add(
          builder.reshape(variance, shape),
          builder.constant(input.dataType, options.epsilon))))),
    builder.reshape(options.bias, shape));
}

8.9.7. cast

入力テンソル内の各要素を対象データ型へキャストする。
partial interface MLGraphBuilder {
  MLOperand cast(MLOperand input,
                 MLOperandDataType dataType,
                 optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits cast;
};
引数:

戻り値: MLOperandinputと同じ形状を持ち、 各要素が対象データ型へキャストされたN次元テンソル。

cast()のテンソル制限
オペランド 許可されるデータ 型 許可されるランク
input 任意 N
output 任意 input同じ

MLOpSupportLimitscast()について次のメンバーを持つ。

cast, 型はMLSingleInputSupportLimits

cast()演算子のサポート制限。

MLOperandDataType間のキャストは、 次の表に従い、一部の場合は規定され、それ以外の場合は実装定義である。

cast() 演算の動作。inputdataType(行)と 対象dataType (列)により与えられる。
対象型 入力型 "float32", "float16" "int32", "uint32", "int64", "uint64", "int8", "uint8"
"float32", "float16" 範囲内であれば、最も近い表現可能な値。

範囲外であれば、+/-Infinity。

範囲内であれば、切り捨てられる。

範囲外であれば、実装定義

"int32", "uint32", "int64", "uint64", "int8", "uint8" 範囲内であれば、最も近い表現可能な値。

範囲外であれば、+/-Infinity。

範囲内であれば、同じ値。

範囲外であれば、符号付き型について2の補数を仮定して、下位Nビットを対象型として再解釈する。

注記: 例えば、"int8"から "uint8"へ-1をキャストすると、 255になるように規定されている。しかし、"float32"から "uint8"へ-1をキャストすることは 実装定義である。

cast(input, dataType, options) メソッドの手順は次のとおりである。
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. dataTypeが(この表に従う)出力テンソルの許可されるデータ型でない場合、TypeErrorthrowする。

  4. グラフ接続を作成する:

    1. operatorを、dataTypeおよびoptionsが与えられた "cast"演算用の演算子とする。

    2. outputを、inputが与えられてMLOperandをコピーする結果とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. operatoroutputoutputに設定する。

  5. outputを返す。

8.9.8. clamp

最小値および最大値により指定される範囲内に、入力テンソルを要素ごとにクランプする。
dictionary MLClampOptions : MLOperatorOptions {
  MLNumber minValue;
  MLNumber maxValue;
};

partial interface MLGraphBuilder {
  MLOperand clamp(MLOperand input, optional MLClampOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits clamp;
};

MLClampOptions は次のメンバーを持つ。

minValue, 型はMLNumber

範囲の最小値。指定されていない場合、範囲の下限でクランプは行われない。

maxValue, 型はMLNumber

範囲の最大値。指定されていない場合、範囲の上限でクランプは行われない。

引数: 戻り値:
clamp()のテンソル制限
オペランド 許可される データ型 許可されるランク
input 任意 N
output input同じ input同じ

MLOpSupportLimitsclamp()について次のメンバーを持つ。

clamp, 型はMLSingleInputSupportLimits

clamp()演算子のサポート制限。

clamp(input, options)メソッドの 手順は次のとおりである。
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. minValueを、与えられていればoptions.minValue、 そうでなければInfinityとする。

  4. options.minValue を、minValueinputdataTypeキャストする結果に設定する。

  5. maxValueを、与えられていればoptions.maxValue、 そうでなければ-Infinityとする。

  6. options.maxValue を、maxValueinputdataTypeキャストする結果に設定する。

  7. options.minValueoptions.maxValueより大きい場合、 TypeErrorthrowする。

  8. グラフ接続を作成する:

    1. outputを、inputが与えられてMLOperandをコピーする結果とする。

    2. operatorを、optionsが与えられた、"clamp"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. operatoroutputoutputに設定する。

  9. outputを返す。

この演算の動作は、次のように他の演算の使用から汎用的にエミュレートできる。 ただし、ユーザーエージェントは通常、より効率的な実装を持つ。 基盤プラットフォームがある演算を直接サポートしない場合、この分解は実装を導くテンプレートとして使用できる。
function clamp(builder, input, options) {
  if (options.minValue === undefined) {
    if (options.maxValue === undefined) {
      return input;
    } else {
      return builder.min(
        input, builder.constant(input.dataType, options.maxValue));
    }
  } else {
    if (options.maxValue === undefined) {
      return builder.max(
        input, builder.constant(input.dataType, options.minValue));
    } else {
      return builder.min(
        builder.max(input, builder.constant(input.dataType, options.minValue)),
        builder.constant(input.dataType, options.maxValue));
    }
  }
}

8.9.9. concat

指定された軸に沿って入力テンソルを連結する。
partial interface MLGraphBuilder {
  MLOperand concat(sequence<MLOperand> inputs,
                   [EnforceRange] unsigned long axis,
                   optional MLOperatorOptions options = {});
};

dictionary MLConcatSupportLimits {
  MLTensorLimits inputs;
  MLTensorLimits output;
};

partial dictionary MLOpSupportLimits {
  MLConcatSupportLimits concat;
};
引数:

戻り値: MLOperand。 すべての入力をaxisに沿って連結したテンソル。 出力テンソルは、すべての入力が連結された次元を除き同じ形状を持つ。 その次元のサイズは、同じ次元におけるすべての入力サイズの合計として計算される。

concat()のテンソル制限
オペランド 許可される データ型 許可されるランク
inputs項目 任意 1からN
output inputs項目同じ inputs項目同じ

MLConcatSupportLimits は次のメンバーを持つ。

inputs, 型はMLTensorLimits

すべての入力オペランド用のMLTensorLimits

output, 型はMLTensorLimits

出力オペランド用のMLTensorLimits

MLOpSupportLimitsconcat()について次のメンバーを持つ。

concat, 型はMLConcatSupportLimits

concat()演算子のサポート制限。

concat(inputs, axis, options) メソッドの手順は次のとおりである。
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputs内の任意の項目とともに行った結果がfalseを返す場合、 TypeErrorthrowする。

  3. inputsサイズ妥当なテンソル数でない場合、TypeErrorthrowする。

  4. firstinputs[0]とする。

  5. axisfirstrank以上である場合、TypeErrorthrowする。

  6. descを、firstdataTypeおよび firstshapeが与えられてMLOperandDescriptorを 作成する結果とする。

  7. desc.shape[axis] をfirstshape[axis]に設定する。

  8. indexについて、1以上 inputsサイズ未満の範囲内で:

    1. inputinputs[index]とする。

    2. inputdataTypefirstdataTypeと等しくない場合、TypeErrorthrowする。

    3. inputrankfirstrankと等しくない場合、 TypeErrorthrowする。

    4. inputrank未満の0以上の範囲内の 各dimについて反復する

      axisにより与えられる次元のものを除き、オペランドの対応する各次元の形状および型が同じでない場合、失敗する。
      1. dimaxisと等しくなく、かつinputshape[dim]が firstshape[dim]と等しくない場合、TypeErrorthrowする。

      2. dimaxisと等しい場合:

        1. sizeを、desc.shape[axis] とinputshape[dim]の合計とする。

        2. size妥当な 次元でない場合、TypeErrorthrowする。

        3. desc.shape[axis] をsizeに設定する。

  9. グラフ接続を作成する:

    1. outputを、thisおよび descが与えられてMLOperandを 作成する結果とする。

    2. operatorを、inputsaxis、およびoptionsが与えられた "concat"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operator入力inputsに設定する。

    5. operatoroutputoutputに設定する。

  10. outputを返す。

8.9.10. conv2d

4次元の入力テンソルおよびフィルターテンソルが与えられたとき、2次元畳み込みを計算する
enum MLConv2dFilterOperandLayout {
  "oihw",
  "hwio",
  "ohwi",
  "ihwo"
};

dictionary MLConv2dOptions : MLOperatorOptions {
  sequence<[EnforceRange] unsigned long> padding;
  sequence<[EnforceRange] unsigned long> strides;
  sequence<[EnforceRange] unsigned long> dilations;
  [EnforceRange] unsigned long groups = 1;
  MLInputOperandLayout inputLayout = "nchw";
  MLConv2dFilterOperandLayout filterLayout = "oihw";
  MLOperand bias;
};

partial interface MLGraphBuilder {
  MLOperand conv2d(MLOperand input,
                   MLOperand filter,
                   optional MLConv2dOptions options = {});
};

dictionary MLConv2dSupportLimits {
  MLTensorLimits input;
  MLTensorLimits filter;
  MLTensorLimits bias;
  MLTensorLimits output;
};

partial dictionary MLOpSupportLimits {
  MLConv2dSupportLimits conv2d;
};

MLConv2dOptions は次のメンバーを持つ。

padding, 型はsequence<[EnforceRange] unsigned long>

長さ4のリスト: [beginningHeight, endingHeight, beginningWidth, endingWidth]。 畳み込み入力の各空間次元の先頭および末尾に追加される行および列を指定する。 デフォルト値は[0, 0, 0, 0]である。

strides, 型はsequence<[EnforceRange] unsigned long>

長さ2のリスト: [strideHeight, strideWidth]。 畳み込み入力の各空間次元に対するスライディングウィンドウのストライドを指定する。 デフォルト値は[1, 1]である。

dilations, 型はsequence<[EnforceRange] unsigned long>

長さ2のリスト: [dilationHeight, dilationWidth]。畳み込みフィルター(カーネル)に適用される 各空間次元の膨張係数を指定する。 デフォルト値は[1, 1]である。

groups, 型はunsigned long、デフォルトは1

入力チャンネルおよび出力チャンネルが分割されるグループ数。

inputLayout, 型はMLInputOperandLayout、デフォルトは "nchw"

入力テンソルおよび出力テンソルのレイアウト形式を次のように指定する。

  • "nchw"

    • 入力テンソル: [batches, inputChannels, height, width]

    • 出力テンソル: [batches, outputChannels, height, width]

  • "nhwc":

    • 入力テンソル: [batches, height, width, inputChannels]

    • 出力テンソル: [batches, height, width, outputChannels]

filterLayout, 型はMLConv2dFilterOperandLayout、デフォルトは "oihw"

フィルターテンソルのレイアウト形式を次のように指定する。

  • "oihw": [outputChannels, inputChannels/groups, height, width]

  • "hwio": [height, width, inputChannels/groups, outputChannels]

  • "ohwi": [outputChannels, height, width, inputChannels/groups]

  • "ihwo": [inputChannels/groups, height, width, outputChannels]

bias, 型はMLOperand

畳み込み結果に値が加算される、[outputChannels]の形状を持つ追加の1次元テンソル。

引数:

戻り値: MLOperand。 畳み込み結果を含む出力4次元テンソル。出力形状は inputLayoutに従って解釈される。 より具体的には、"nchw" 入力レイアウトの場合、出力テンソルの空間次元または末尾2次元のサイズは次のように計算できる。

outputSize = 1 + (inputSize - (filterSize - 1) * dilation - 1 + beginningPadding + endingPadding) / stride

conv2d()のテンソル制限
オペランド 許可される データ型 許可されるランク
input "float32", "float16" 4
filter input同じ 4
bias input同じ 1
output input同じ 4

MLConv2dSupportLimits は次のメンバーを持つ。

input, 型はMLTensorLimits

入力オペランド用のMLTensorLimits

filter, 型はMLTensorLimits

filterオペランド用のMLTensorLimits

bias, 型はMLTensorLimits

biasオペランド用のMLTensorLimits

output, 型はMLTensorLimits

出力オペランド用のMLTensorLimits

MLOpSupportLimitsconv2d()について次のメンバーを持つ。

conv2d, 型はMLConv2dSupportLimits

conv2d()演算子のサポート制限。

depthwise conv2d演算は、MobileNetのようなモデルで使用されるグループ化畳み込みの一種であり、 groups = inputChannels = outputChannelsで、フィルターテンソルの形状は、"oihw" レイアウトでは[options.groups, 1, height, width]"hwio" レイアウトでは[height, width, 1, options.groups]"ohwi" レイアウトでは[options.groups, height, width, 1]"ihwo" レイアウトでは[1, height, width, options.groups]である。
unsigned整数inputSizefilterSizebeginningPaddingendingPaddingstrideおよびdilationが与えられたとき、 conv出力サイズを計算するには、次の手順を実行する。 これらは数値を返す。
  1. effectiveFilterSizeを ( filterSize - 1 ) * dilation + 1 とする。

  2. outputSizeを ( inputSize - effectiveFilterSize + beginningPadding + endingPadding ) / stride + 1 とする。

  3. outputSizeを返す。

unsigned整数inputHeightinputWidthfilterHeightおよび filterWidth、4個のunsigned整数のリストpadding、2個のunsigned整数のリスト strides、および2個のunsigned整数のリストdilationsが与えられたとき、 conv2d出力サイズを計算するには、次の手順を実行する。 これらは2個の数値のリストを返す。
  1. outputHeightを、inputHeightfilterHeightpadding[0]、 padding[1]、strides[0]およびdilations[0]が与えられて conv出力サイズを計算する結果とする。

  2. outputWidthを、inputWidthfilterWidthpadding[2]、 padding[3]、strides[1]およびdilations[1]が与えられて conv出力サイズを計算する結果とする。

  3. « outputHeight, outputWidth »を返す。

conv2d(input, filter, options) メソッドの手順は次のとおりである。
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することを、thisおよびinputfilter、および options.bias (それが存在する場合)のいずれかとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. inputdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

  4. inputrankがその許可されるランクでない場合、TypeErrorthrowする。

  5. filterrankがその許可されるランクでない場合、TypeErrorthrowする。

  6. filterdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

  7. options.padding存在しない場合、それをリスト« 0, 0, 0, 0 »に設定する。

  8. そうでなく、options.paddingサイズが4でない場合、TypeErrorthrowする。

  9. options.strides存在しない場合、それをリスト« 1, 1 »に設定する。

  10. そうでなく、options.stridesサイズが2でない場合、TypeErrorthrowする。

  11. options.strides 内の任意の項目が0と等しい場合、TypeErrorthrowする。

  12. options.dilations存在しない場合、それをリスト« 1, 1 »に設定する。

  13. そうでなく、options.dilationsサイズが2でない場合、TypeErrorthrowする。

  14. options.dilations 内の任意の項目が0と等しい場合、TypeErrorthrowする。

  15. options.groups が0である場合、TypeErrorthrowする。

  16. 出力形状を計算する:

    1. inputShapeinputshapeとする。

    2. options.inputLayoutで分岐する。

      "nchw"

      « batches, inputChannels, inputHeight, inputWidth »をinputShapeとする。

      "nhwc"

      « batches, inputHeight, inputWidth, inputChannels »をinputShapeとする。

    3. filterShapefiltershapeとする。

    4. options.filterLayoutで分岐する。

      "hwio"

      « filterHeight, filterWidth, filterInputChannels, outputChannels »を filterShapeとする。

      "ohwi"

      « outputChannels, filterHeight, filterWidth, filterInputChannels »をfilterShapeとする。

      "ihwo"

      « filterInputChannels, filterHeight, filterWidth, outputChannels »をfilterShapeとする。

      "oihw"

      « outputChannels, filterInputChannels, filterHeight, filterWidth »をfilterShapeとする。

    5. inputChannels % options.groups が0でない場合、TypeErrorthrowする。

    6. そうでなく、inputChannels / options.groupsfilterInputChannelsと等しくない場合、TypeErrorthrowする。

    7. outputChannels % options.groups が0でない場合、TypeErrorthrowする。

    8. options.bias存在する場合:

      1. そのshapeが« outputChannels »と等しくない場合、TypeErrorthrowする。

      2. そのdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

    9. « outputHeight, outputWidth »を、inputHeightinputWidthfilterHeightfilterWidthoptions.paddingoptions.strides、 およびoptions.dilations が与えられてconv2d出力サイズを 計算する結果とする。

    10. outputHeightをfloor( outputHeight )に設定する。

    11. outputWidthをfloor( outputWidth )に設定する。

    12. outputHeightまたはoutputWidthのいずれかが妥当な 次元でない場合、TypeErrorthrowする。

    13. options.inputLayoutで分岐する。

      "nchw"

      outputShapeを« batches, outputChannels, outputHeight, outputWidth »とする。

      "nhwc"

      outputShapeを« batches, outputHeight, outputWidth, outputChannels »とする。

    14. descを、inputdataTypeおよびoutputShapeが与えられてMLOperandDescriptorを作成する 結果とする。

  17. グラフ接続を作成する:

    1. outputを、thisおよび descが与えられてMLOperandを 作成する結果とする。

    2. operatorを、optionsおよびfilterが与えられた "conv2d"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operator入力inputおよびfilterに設定する。

    5. options.bias存在する場合、それをoperator入力へ追加する。

    6. operatoroutputoutputに設定する。

  18. outputを返す。

8.9.11. convTranspose2d

4次元の入力テンソルおよびフィルターテンソルが与えられたとき、2次元転置畳み込みを計算する
enum MLConvTranspose2dFilterOperandLayout {
  "iohw",
  "hwoi",
  "ohwi"
};

dictionary MLConvTranspose2dOptions : MLOperatorOptions {
  sequence<[EnforceRange] unsigned long> padding;
  sequence<[EnforceRange] unsigned long> strides;
  sequence<[EnforceRange] unsigned long> dilations;
  sequence<[EnforceRange] unsigned long> outputPadding;
  sequence<[EnforceRange] unsigned long> outputSizes;
  [EnforceRange] unsigned long groups = 1;
  MLInputOperandLayout inputLayout = "nchw";
  MLConvTranspose2dFilterOperandLayout filterLayout = "iohw";
  MLOperand bias;
};

partial interface MLGraphBuilder {
  MLOperand convTranspose2d(MLOperand input, MLOperand filter,
                            optional MLConvTranspose2dOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLConv2dSupportLimits convTranspose2d;
};

MLConvTranspose2dOptions は次のメンバーを持つ。

padding, 型はsequence<[EnforceRange] unsigned long>

長さ4のリスト: [beginningHeight, endingHeight, beginningWidth, endingWidth]。 畳み込み入力の各空間次元の先頭および末尾に追加される行および列を指定する。 デフォルト値は[0, 0, 0, 0]である。

strides, 型はsequence<[EnforceRange] unsigned long>

長さ2のリスト: [strideHeight, strideWidth]。 畳み込み入力の各空間次元に対するスライディングウィンドウのストライドを指定する。 デフォルト値は[1, 1]である。

dilations, 型はsequence<[EnforceRange] unsigned long>

長さ2のリスト: [dilationHeight, dilationWidth]。畳み込みフィルター(カーネル)に適用される 各空間次元の膨張係数を指定する。 デフォルト値は[1, 1]である。

outputPadding, 型は sequence<[EnforceRange] unsigned long>

長さ2のリスト。 出力テンソルの各空間次元に適用されるパディング値を指定する。strides の値が1より大きい場合、転置畳み込みに対する出力テンソル形状の曖昧さを解消するために、明示的な パディング値が必要である。

これらの値は、必要なときに出力形状の曖昧さを解消するためにのみ使用されることに注意されたい。 必ずしも何らかのパディング値が出力テンソルへ書き込まれることを引き起こすわけではない。

デフォルト値は[0, 0]である。

outputSizes, 型はsequence<[EnforceRange] unsigned long>

長さ2のリスト。 出力テンソルの末尾2次元のサイズを指定する。出力サイズが明示的に指定された場合、outputPadding 内の出力パディング値は無視される。

指定されない場合、出力サイズは自動的に計算される。

groups, 型はunsigned long、デフォルトは1

入力チャンネルおよび出力チャンネルが分割されるグループ数。

inputLayout, 型はMLInputOperandLayout、デフォルトは "nchw"

入力テンソルおよび出力テンソルのレイアウト形式を次のように指定する。

  • "nchw"

    • 入力テンソル: [batches, inputChannels, height, width]

    • 出力テンソル: [batches, outputChannels, height, width]

  • "nhwc":

    • 入力テンソル: [batches, height, width, inputChannels]

    • 出力テンソル: [batches, height, width, outputChannels]

filterLayout, 型はMLConvTranspose2dFilterOperandLayout、 デフォルトは"iohw"

フィルターテンソルのレイアウト形式を次のように指定する。

  • "iohw": [inputChannels, outputChannels/groups, height, width]

  • "hwoi": [height, width, outputChannels/groups, inputChannels]

  • "ohwi": [outputChannels/groups, height, width, inputChannels]

bias, 型はMLOperand

畳み込み結果に値が加算される、[outputChannels]の形状を持つ追加の1次元テンソル。

引数:

戻り値: MLOperand。 転置畳み込み結果を含む出力4次元テンソル。出力形状は inputLayoutに従って解釈される。 より具体的には、outputSizes が明示的に指定されない限り、次のように出力テンソルの空間次元値を計算するためにoutputPadding が必要である。

outputSize = (inputSize - 1) * stride + (filterSize - 1) * dilation + 1 - beginningPadding - endingPadding + outputPadding

convTranspose2d()のテンソル制限
オペランド 許可される データ型 許可されるランク
input "float32", "float16" 4
filter input同じ 4
bias input同じ 1
output input同じ 4

MLOpSupportLimitsconvTranspose2d()について次のメンバーを持つ。

convTranspose2d, 型は MLConv2dSupportLimits

convTranspose2d()演算子のサポート制限。

unsigned整数inputSizefilterSizebeginningPaddingendingPaddingstride、およびdilationが与えられたとき、 convtranspose出力サイズを計算するには、 次の手順を実行する。これらは数値を返す。
  1. effectiveFilterSizeを ( filterSize - 1 ) * dilation + 1 とする。

  2. outputSizeを ( inputSize - 1 ) * stride + effectiveFilterSize - beginningPadding - endingPadding とする。

  3. outputSizeを返す。

convTranspose2d(input, filter, options) メソッドの手順は次のとおりである。
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することを、thisおよびinputfilter、および options.bias (それが存在する場合)のいずれかとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. inputrankがその許可されるランクでない場合、TypeErrorthrowする。

  4. inputdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

  5. filterrankがその許可されるランクでない場合、TypeErrorthrowする。

  6. filterdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

  7. options.padding存在しない場合、それをリスト« 0, 0, 0, 0 »に設定する。

  8. そうでなく、options.paddingサイズが4でない場合、TypeErrorthrowする。

  9. options.strides存在しない場合、それをリスト« 1, 1 »に設定する。

  10. そうでなく、options.stridesサイズが2でない場合、TypeErrorthrowする。

  11. options.strides 内の任意の項目が0と等しい場合、TypeErrorthrowする。

  12. options.dilations存在しない場合、それをリスト« 1, 1 »に設定する。

  13. そうでなく、options.dilationsサイズが2でない場合、TypeErrorthrowする。

  14. options.dilations 内の任意の項目が0と等しい場合、TypeErrorthrowする。

  15. options.outputPadding存在しない場合、それをリスト« 0, 0 »に設定する。

  16. そうでなく、options.outputPaddingサイズが2でない場合、TypeErrorthrowする。

  17. options.outputSizes存在する場合:

    1. そのサイズが2でない場合、TypeErrorthrowする。

  18. そうでなければ:

    1. options.outputPadding[0] がoptions.strides[0]以上である場合、 またはoptions.outputPadding[1] がoptions.strides[1]以上である場合、 TypeErrorthrowする。

  19. options.groups が0である場合、TypeErrorthrowする。

  20. 出力形状を計算する:

    1. inputShapeinputshapeとする。

    2. options.inputLayoutで分岐する。

      "nchw"

      « batches, inputChannels, inputHeight, inputWidth »をinputShapeとする。

      "nhwc"

      « batches, inputHeight, inputWidth, inputChannels »をinputShapeとする。

    3. filterShapefiltershapeとする。

    4. options.filterLayoutで分岐する。

      "iohw"

      « filterInputChannels, filterOutputChannels, filterHeight, filterWidth »をfilterShapeとする。

      "hwoi"

      « filterHeight, filterWidth, filterOutputChannels, filterInputChannels »を filterShapeとする。

      "ohwi"

      « filterOutputChannels, filterHeight, filterWidth, filterInputChannels »を filterShapeとする。

    5. inputChannelsfilterInputChannelsと等しくない場合、TypeErrorthrowする。

    6. outputChannelsfilterOutputChannels * options.groupsとする。

    7. outputChannels妥当な次元でない場合、TypeErrorthrowする。

    8. options.bias存在する場合:

      1. そのshapeが« outputChannels »と等しくない場合、TypeErrorthrowする。

      2. そのdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

    9. calculatedOutputHeightを、inputHeightfilterHeightpadding[0]、padding[1]、strides[0]および dilations[0]が与えられてconvtranspose出力サイズを 計算する結果とする。

    10. calculatedOutputWidthを、inputWidthfilterWidthpadding[2]、padding[3]、strides[1]および dilations[1]が与えられてconvtranspose出力サイズを 計算する結果とする。

    11. options.outputSizes存在する場合:

      1. « outputHeight, outputWidth »を options.outputSizesとする。

      2. outputHeightcalculatedOutputHeight未満、または calculatedOutputHeight + strides[0]以上である場合、TypeErrorthrowする。

      3. outputWidthcalculatedOutputWidth未満、または calculatedOutputWidth + strides[1]以上である場合、TypeErrorthrowする。

    12. そうでなければ:

      1. outputHeightcalculatedOutputHeight + options.outputPadding[0]とする。

      2. outputWidthcalculatedOutputWidth + options.outputPadding[1]とする。

    13. outputHeightまたはoutputWidthのいずれかが妥当な 次元でない場合、TypeErrorthrowする。

    14. options.inputLayoutで分岐する。

      "nchw"

      outputShapeを« batches, outputChannels, floor( outputHeight ), floor( outputWidth ) »とする。

      "nhwc"

      outputShapeを« batches, floor( outputHeight ), floor( outputWidth ), outputChannels »とする。

    15. descを、inputdataTypeおよびoutputShapeが与えられてMLOperandDescriptorを作成する 結果とする。

  21. グラフ接続を作成する:

    1. outputを、thisおよび descが与えられてMLOperandを 作成する結果とする。

    2. operatorを、optionsおよびfilterが与えられた "convTranspose2d"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operator入力inputおよびfilterに設定する。

    5. options.bias存在する場合、それをoperator入力へ追加する。

    6. operatoroutputoutputに設定する。

  22. outputを返す。

8.9.12. cumulativeSum

与えられた軸に沿って、一連の値の累積和を、現在の値を含めるか除外するかのいずれかで計算する。
dictionary MLCumulativeSumOptions : MLOperatorOptions {
  boolean exclusive = false;
  boolean reversed = false;
};

partial interface MLGraphBuilder {
  MLOperand cumulativeSum(MLOperand input,
                          unsigned long axis,
                          optional MLCumulativeSumOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits cumulativeSum;
};
cumulativeSum()のテンソル制限
オペランド 許可される データ型 許可されるランク
input "float32", "float16", "int32", "uint32", "int64", "uint64" 1からN
output input同じ input同じ

MLCumulativeSumOptions は次のメンバーを持つ。

exclusive, 型はboolean、デフォルトはfalse

出力に現在の値を含めるか除外するか、すなわち包含的prefix sumか排他的prefix sumかを示す [Prefix-sum]。入力[1,2,3,4]が与えられた場合、包含的な合計は [1,3,6,10]の出力を生成する一方、排他的な合計は[0,1,3,6]を生成する。 デフォルトは包含的である。

reversed, 型はboolean、デフォルトはfalse

有効な軸に沿った合計方向を逆にし、代わりに高い座標から低い座標へ開始するかどうかを示す。 入力[1,2,3,4]が与えられた場合、包含的な前方向の合計は[1,3,6,10]の出力を生成する一方、 包含的な後方向の合計は[10,9,7,4]を生成する。デフォルトは前方向である。

引数:

戻り値:

MLOpSupportLimitscumulativeSum()について次のメンバーを持つ。

cumulativeSum, 型は MLSingleInputSupportLimits

cumulativeSum()演算子のサポート制限。

cumulativeSum(input, axis, options) メソッドの手順は次のとおりである。
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. inputdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

  4. axisinputrank以上である場合、TypeErrorthrowする。

  5. グラフ接続を作成する:

    1. outputを、inputが与えられてMLOperandをコピーする結果とする。

    2. operatorを、"cumulativeSum"演算およびoptions用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. operatoroutputoutputに設定する。

  6. outputを返す。

8.9.13. 要素ごとの二項演算

2つの入力テンソルの要素ごとの二項加算、減算、乗算、除算、累乗、最大値、および最小値を計算する。

演算は、[numpy-broadcasting-rule]に従ってブロードキャスト される。入力テンソルは双方向ブロードキャスト可能でなければならない。出力テンソルのrankは、入力テンソルの最大rankである。 出力テンソルの各次元について、そのサイズは、入力テンソルのその次元に沿った最大サイズである。

partial interface MLGraphBuilder {
  MLOperand add(MLOperand a, MLOperand b, optional MLOperatorOptions options = {});
  MLOperand sub(MLOperand a, MLOperand b, optional MLOperatorOptions options = {});
  MLOperand mul(MLOperand a, MLOperand b, optional MLOperatorOptions options = {});
  MLOperand div(MLOperand a, MLOperand b, optional MLOperatorOptions options = {});
  MLOperand max(MLOperand a, MLOperand b, optional MLOperatorOptions options = {});
  MLOperand min(MLOperand a, MLOperand b, optional MLOperatorOptions options = {});
  MLOperand pow(MLOperand a, MLOperand b, optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLBinarySupportLimits add;
  MLBinarySupportLimits sub;
  MLBinarySupportLimits mul;
  MLBinarySupportLimits div;
  MLBinarySupportLimits max;
  MLBinarySupportLimits min;
  MLBinarySupportLimits pow;
};
引数:

戻り値: MLOperand。 2つの入力テンソルの要素ごとの二項演算の結果を含む出力テンソル。

演算の種類:
要素ごとの二項オプションのテンソル制限
オペランド 許可される データ型 許可されるランク
a 任意 N
b a同じ N
output a同じ N

MLOpSupportLimits は要素ごとの二項演算について次のメンバーを持つ。

add, 型はMLBinarySupportLimits

add()演算子のサポート制限。

sub, 型はMLBinarySupportLimits

sub()演算子のサポート制限。

mul, 型はMLBinarySupportLimits

mul()演算子のサポート制限。

div, 型はMLBinarySupportLimits

div()演算子のサポート制限。

max, 型はMLBinarySupportLimits

max()演算子のサポート制限。

min, 型はMLBinarySupportLimits

min()演算子のサポート制限。

pow, 型はMLBinarySupportLimits

pow()演算子のサポート制限。

文字列opMLOperand aMLOperand b、およびMLOperatorOptions optionsが与えられたとき、要素ごとの 二項演算を作成するには、次の手順を実行する。
  1. Assert: opは"add"、"sub"、"mul"、"div"、"max"、 "min"、"pow"のいずれかである。

  2. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  3. オペランドを検証することをthisおよびabのいずれかとともに行った結果がfalseを返す場合、 TypeErrorthrowする。

  4. adataTypebdataTypeと等しくない場合、TypeErrorthrowする。

  5. outputShapeを、ashapebshape双方向ブロードキャストする結果とする。

    1. それが失敗を返す場合、TypeErrorthrowする。

  6. descriptorを、adataTypeおよび outputShapeが与えられてMLOperandDescriptorを 作成する結果とする。

  7. グラフ接続を作成する:

    1. outputを、thisおよび descriptorが与えられてMLOperandを 作成する結果とする。

    2. operatorを、ab、およびoptionsが与えられた op演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operator入力aおよびbに設定する。

    5. operatoroutputoutputに設定する。

  8. outputを返す。

要素ごとの二項演算アルゴリズムは、次のように要素ごとの二項演算を作成する 手順を呼び出す。
add(a, b, options) メソッドの手順は次のとおりである。
  1. outputを、"add"、ab、およびoptionsが与えられて要素ごとの二項演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

sub(a, b, options) メソッドの手順は次のとおりである。
  1. outputを、"sub"、ab、およびoptionsが与えられて要素ごとの二項演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

mul(a, b, options) メソッドの手順は次のとおりである。
  1. outputを、"mul"、ab、およびoptionsが与えられて要素ごとの二項演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

div(a, b, options) メソッドの手順は次のとおりである。
  1. outputを、"div"、ab、およびoptionsが与えられて要素ごとの二項演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

max(a, b, options) メソッドの手順は次のとおりである。
  1. outputを、"max"、ab、およびoptionsが与えられて要素ごとの二項演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

min(a, b, options) メソッドの手順は次のとおりである。
  1. outputを、"min"、ab、およびoptionsが与えられて要素ごとの二項演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

pow(a, b, options) メソッドの手順は次のとおりである。
  1. outputを、"pow"、ab、およびoptionsが与えられて要素ごとの二項演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

8.9.14. 要素ごとの論理演算

入力テンソルを要素ごとに比較し、その比較について値0(false)または1(true)の"uint8" テンソルを返す。単一オペランド演算については、その演算の論理結果を返す。

複数オペランド演算については、演算は[numpy-broadcasting-rule]に従ってブロードキャストされる。入力テンソルは双方向ブロードキャスト可能でなければならない。出力テンソルのrankは、入力テンソルの最大rankである。 出力テンソルの各次元について、そのサイズは、入力テンソルのその次元に沿った最大サイズである。

partial interface MLGraphBuilder {
  MLOperand equal(MLOperand a,
                  MLOperand b,
                  optional MLOperatorOptions options = {});
  MLOperand notEqual(MLOperand a,
                     MLOperand b,
                     optional MLOperatorOptions options = {});
  MLOperand greater(MLOperand a,
                    MLOperand b,
                    optional MLOperatorOptions options = {});
  MLOperand greaterOrEqual(MLOperand a,
                           MLOperand b,
                           optional MLOperatorOptions options = {});
  MLOperand lesser(MLOperand a,
                   MLOperand b,
                   optional MLOperatorOptions options = {});
  MLOperand lesserOrEqual(MLOperand a,
                          MLOperand b,
                          optional MLOperatorOptions options = {});
  MLOperand logicalNot(MLOperand a, optional MLOperatorOptions options = {});
  MLOperand logicalAnd(MLOperand a,
                       MLOperand b,
                       optional MLOperatorOptions options = {});
  MLOperand logicalOr(MLOperand a,
                      MLOperand b,
                      optional MLOperatorOptions options = {});
  MLOperand logicalXor(MLOperand a,
                       MLOperand b,
                       optional MLOperatorOptions options = {});
  MLOperand isNaN(MLOperand a, optional MLOperatorOptions options = {});
  MLOperand isInfinite(MLOperand a, optional MLOperatorOptions options = {});
};

dictionary MLLogicalNotSupportLimits {
  MLTensorLimits a;
  MLTensorLimits output;
};

partial dictionary MLOpSupportLimits {
  MLBinarySupportLimits equal;
  MLBinarySupportLimits notEqual;
  MLBinarySupportLimits greater;
  MLBinarySupportLimits greaterOrEqual;
  MLBinarySupportLimits lesser;
  MLBinarySupportLimits lesserOrEqual;
  MLLogicalNotSupportLimits logicalNot;
  MLBinarySupportLimits logicalAnd;
  MLBinarySupportLimits logicalOr;
  MLBinarySupportLimits logicalXor;
  MLLogicalNotSupportLimits isNaN;
  MLLogicalNotSupportLimits isInfinite;
};
引数:

戻り値: MLOperand。 2つの入力テンソルの要素ごとの比較結果を含む出力テンソル。

要素ごとの論理オプションのテンソル制限
オペランド 許可される データ型 許可されるランク
a 演算手順の一部として指定される N
b a同じ N
output "uint8" N

MLLogicalNotSupportLimits は次のメンバーを持つ。

a, 型はMLTensorLimits

aオペランド用のMLTensorLimits

output, 型はMLTensorLimits

出力オペランド用のMLTensorLimits

MLOpSupportLimits は要素ごとの論理演算について次のメンバーを持つ。

equal, 型はMLBinarySupportLimits

equal()演算子のサポート制限。

notEqual, 型はMLBinarySupportLimits

notEqual()演算子のサポート制限。

greater, 型はMLBinarySupportLimits

greater()演算子のサポート制限。

greaterOrEqual, 型は MLBinarySupportLimits

greaterOrEqual()演算子のサポート制限。

lesser, 型はMLBinarySupportLimits

lesser()演算子のサポート制限。

lesserOrEqual, 型は MLBinarySupportLimits

lesserOrEqual()演算子のサポート制限。

logicalNot, 型はMLLogicalNotSupportLimits

logicalNot()演算子のサポート制限。

logicalAnd, 型はMLBinarySupportLimits

logicalAnd()演算子のサポート制限。

logicalOr, 型はMLBinarySupportLimits

logicalOr()演算子のサポート制限。

logicalXor, 型はMLBinarySupportLimits

logicalXor()演算子のサポート制限。

isNaN, 型はMLLogicalNotSupportLimits

isNaN()演算子のサポート制限。

isInfinite, 型はMLLogicalNotSupportLimits

isInfinite()演算子のサポート制限。

演算の種類:
greaterOrEqual() およびlesserOrEqual() 演算は、それぞれlogicalNot()lesser()、 およびgreater() 演算の観点から実装できるが (言い換えると、builder.greaterOrEqual(a, b)builder.logicalNot(builder.lesser(a, b))である)、NaNケースを扱うため、および二重比較を避ける性能上の理由から、 それらは明示的に定義されている。
文字列opMLOperand a、任意のMLOperand b、およびMLOperatorOptions optionsが与えられたとき、要素ごとの論理演算を作成するには、次の手順を実行する。
  1. Assert: opは"equal"、"notEqual"、"greater"、 "greaterOrEqual"、"lesser"、"lesserOrEqual"、"logicalNot"、"logicalAnd"、"logicalOr"、 "logicalXor"、"isNaN"、"isInfinite"のいずれかである。

  2. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  3. オペランドを検証することをthisおよびaとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  4. opが"logicalNot"、"logicalAnd"、"logicalOr"、"logicalXor"のいずれかである場合:

    1. adataType"uint8"でない場合、 TypeErrorthrowする。

  5. opが"isNaN"、"isInfinite"のいずれかである場合:

    1. adataTypeが« "float32", "float16" »のいずれでもない場合、TypeErrorthrowする。

  6. bが渡された場合:

    1. オペランドを検証することをthisおよびbとともに行った結果がfalseを返す場合、TypeErrorthrowする。

    2. adataTypebdataTypeと等しくない場合、TypeErrorthrowする。

    3. outputShapeを、ashapeおよびbshape双方向ブロードキャストする結果とする。 それが失敗を返す場合、TypeErrorthrowする。

  7. そうでなければ:

    1. outputShapeを、ashapeclone とする。

  8. descriptorを、"uint8" およびoutputShapeが与えられてMLOperandDescriptorを 作成する結果とする。

  9. グラフ接続を作成する:

    1. outputを、thisおよび descriptorが与えられてMLOperandを 作成する結果とする。

    2. operatorを、a、および(bが渡された場合は)b、 およびoptionsが与えられたop演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operator入力aおよび(bが 渡された場合は)bに設定する。

    5. operatoroutputoutputに設定する。

  10. outputを返す。

要素ごとの論理演算アルゴリズムは、次のように要素ごとの論理演算を作成する 手順を呼び出す。
equal(a, b, options) メソッドの手順は次のとおりである。
  1. outputを、"equal"、ab、およびoptionsが与えられて要素ごとの論理演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

notEqual(a, b, options) メソッドの手順は次のとおりである。
  1. outputを、"notEqual"、ab、およびoptionsが与えられて要素ごとの論理演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

greater(a, b, options) メソッドの手順は次のとおりである。
  1. outputを、"greater"、ab、およびoptionsが与えられて要素ごとの論理演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

greaterOrEqual(a, b, options) メソッドの手順は次のとおりである。
  1. outputを、"greaterOrEqual"、ab、および optionsが与えられて要素ごとの論理演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

lesser(a, b, options) メソッドの手順は次のとおりである。
  1. outputを、"lesser"、ab、およびoptionsが与えられて要素ごとの論理演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

lesserOrEqual(a, b, options) メソッドの手順は次のとおりである。
  1. outputを、"lesserOrEqual"、ab、およびoptionsが与えられて要素ごとの論理演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

logicalNot(a, options) メソッドの手順は次のとおりである。
  1. outputを、"logicalNot"、a、およびoptionsが与えられて要素ごとの論理演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

logicalAnd(a, b, options) メソッドの手順は次のとおりである。
  1. outputを、"logicalAnd"、ab、およびoptionsが与えられて要素ごとの論理演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

logicalOr(a, b, options) メソッドの手順は次のとおりである。
  1. outputを、"logicalOr"、ab、およびoptionsが与えられて要素ごとの論理演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

logicalXor(a, b, options) メソッドの手順は次のとおりである。
  1. outputを、"logicalXor"、ab、およびoptionsが与えられて要素ごとの論理演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

isNaN(a, options)メソッドの 手順は次のとおりである。
  1. outputを、"isNaN"、a、およびoptionsが与えられて要素ごとの論理演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

isInfinite(a, options) メソッドの手順は次のとおりである。
  1. outputを、"isInfinite"、a、およびoptionsが与えられて要素ごとの論理演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

8.9.15. 要素ごとの単項演算

入力テンソルに対して要素ごとの単項演算を計算する。
partial interface MLGraphBuilder {
  MLOperand abs(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand ceil(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand cos(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand erf(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand exp(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand floor(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand identity(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand log(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand neg(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand reciprocal(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand roundEven(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand sin(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand sign(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand sqrt(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand tan(MLOperand input, optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits abs;
  MLSingleInputSupportLimits ceil;
  MLSingleInputSupportLimits cos;
  MLSingleInputSupportLimits erf;
  MLSingleInputSupportLimits exp;
  MLSingleInputSupportLimits floor;
  MLSingleInputSupportLimits identity;
  MLSingleInputSupportLimits log;
  MLSingleInputSupportLimits neg;
  MLSingleInputSupportLimits reciprocal;
  MLSingleInputSupportLimits roundEven;
  MLSingleInputSupportLimits sin;
  MLSingleInputSupportLimits sign;
  MLSingleInputSupportLimits sqrt;
  MLSingleInputSupportLimits tan;
};
引数:

戻り値: MLOperand。 入力テンソルの要素ごとの単項演算の結果を含む出力テンソル。 出力テンソルの形状は、入力テンソルの形状と同じである。

要素ごとの単項オプションのテンソル制限
オペランド 許可される データ型 許可されるランク
input 演算手順の一部として指定される N
output input同じ input同じ

MLOpSupportLimits は要素ごとの単項演算について次のメンバーを持つ。

abs, 型はMLSingleInputSupportLimits

abs()演算子のサポート制限。

ceil, 型はMLSingleInputSupportLimits

ceil()演算子のサポート制限。

cos, 型はMLSingleInputSupportLimits

cos()演算子のサポート制限。

erf, 型はMLSingleInputSupportLimits

erf()演算子のサポート制限。

exp, 型はMLSingleInputSupportLimits

exp()演算子のサポート制限。

floor, 型はMLSingleInputSupportLimits

floor()演算子のサポート制限。

identity, 型はMLSingleInputSupportLimits

identity()演算子のサポート制限。

log, 型はMLSingleInputSupportLimits

log()演算子のサポート制限。

neg, 型はMLSingleInputSupportLimits

neg()演算子のサポート制限。

reciprocal, 型はMLSingleInputSupportLimits

reciprocal()演算子のサポート制限。

roundEven, 型はMLSingleInputSupportLimits

roundEven()演算子のサポート制限。

sin, 型はMLSingleInputSupportLimits

sin()演算子のサポート制限。

sign, 型はMLSingleInputSupportLimits

sign()演算子のサポート制限。

sqrt, 型はMLSingleInputSupportLimits

sqrt()演算子のサポート制限。

tan, 型はMLSingleInputSupportLimits

tan()演算子のサポート制限。

演算の種類:
文字列opMLOperand input、任意のリストallowedDataTypes、およびoptionsが与えられたとき、 要素ごとの 単項演算を作成するには、次の手順を実行する。
  1. Assert: opは"abs"、"ceil"、"cos"、"erf"、"exp"、 "floor"、"identity"、"log"、"neg"、"reciprocal"、"roundEven"、"sin"、"sign"、"sqrt"、"tan"のいずれかである。

  2. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  3. オペランドを検証することをthisおよびinputとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  4. allowedDataTypesが与えられ、かつそれがinputdataType含まない場合、TypeErrorthrowする。

  5. グラフ接続を作成する:

    1. outputを、inputが与えられてMLOperandをコピーする結果とする。

    2. operatorを、optionsが与えられたop演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. operatoroutputoutputに設定する。

  6. outputを返す。

要素ごとの単項演算アルゴリズムは、次のように要素ごとの単項演算を作成する手順を 呼び出す。
abs(input, options)メソッドの 手順は次のとおりである。
  1. outputを、"abs"、input、« "float32", "float16", "int64", "int32", "int8" »、およびoptionsが与えられて要素ごとの単項演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

ceil(input, options)メソッドの 手順は次のとおりである。
  1. outputを、"ceil"、input、« "float32", "float16" »、およびoptionsが与えられて要素ごとの単項演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

cos(input, options)メソッドの 手順は次のとおりである。
  1. outputを、"cos"、input、« "float32", "float16" »、およびoptionsが与えられて要素ごとの単項演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

erf(input, options)メソッドの 手順は次のとおりである。
  1. outputを、"erf"、input、« "float32", "float16" »、およびoptionsが与えられて要素ごとの単項演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

exp(input, options)メソッドの 手順は次のとおりである。
  1. outputを、"exp"、input、« "float32", "float16" »、およびoptionsが与えられて要素ごとの単項演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

floor(input, options)メソッドの 手順は次のとおりである。
  1. outputを、"floor"、input、« "float32", "float16" »、およびoptionsが与えられて要素ごとの単項演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

identity(input, options) メソッドの手順は次のとおりである。
  1. outputを、"identity"、input、およびoptionsが与えられて要素ごとの単項演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

log(input, options)メソッドの 手順は次のとおりである。
  1. outputを、"log"、input、« "float32", "float16" »、およびoptionsが与えられて要素ごとの単項演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

neg(input, options)メソッドの 手順は次のとおりである。
  1. outputを、"neg"、input、« "float32", "float16", "int64", "int32", "int8" »、およびoptionsが与えられて要素ごとの単項演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

reciprocal(input, options) メソッドの手順は次のとおりである。
  1. outputを、"reciprocal"、input、« "float32", "float16" »、およびoptionsが与えられて要素ごとの単項演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

roundEven(input, options) メソッドの手順は次のとおりである。
  1. outputを、"roundEven"、input、« "float32", "float16" »、およびoptionsが与えられて要素ごとの単項演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

sin(input, options)メソッドの 手順は次のとおりである。
  1. outputを、"sin"、input、« "float32", "float16" »、およびoptionsが与えられて要素ごとの単項演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

sign(input, options)メソッドの 手順は次のとおりである。
  1. outputを、"sign"、input、« "float32", "float16", "int64", "int32", "int8" »、およびoptionsが与えられて要素ごとの単項演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

sqrt(input, options)メソッドの 手順は次のとおりである。
  1. outputを、"sqrt"、input、« "float32", "float16" »、およびoptionsが与えられて要素ごとの単項演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

tan(input, options)メソッドの 手順は次のとおりである。
  1. outputを、"tan"、input、« "float32", "float16" »、およびoptionsが与えられて要素ごとの単項演算を 作成する結果とする。

    1. それがエラーをthrowする場合、そのエラーを再throwする。

  2. outputを返す。

sign() 演算の振る舞いは、ユーザーエージェントは通常より効率的な実装を持つものの、次のように他の演算の使用から 一般的にエミュレートできる。基盤となるプラットフォームが演算を直接サポートしない場合、この分解は 実装を導くためのテンプレートとして使用できる。
function sign(builder, input, options) {
  const zero = builder.constant(input.dataType, 0);
  const positiveOne = builder.constant(input.dataType, 1);
  const negativeOne = builder.constant(input.dataType, -1);

  return builder.where(
    builder.greater(input, zero),
    positiveOne,
    builder.where(builder.lesser(input, zero), negativeOne, zero));
}

8.9.16. dequantizeLinear

使用 scale 和 zero-point 偏置将整数张量反量化为浮点张量,其中 output = (input - zeroPoint) * scalescalezeroPoint 张量可以小于 input 张量,因为它们是按块可广播的。
partial interface MLGraphBuilder {
  MLOperand dequantizeLinear(MLOperand input,
                             MLOperand scale,
                             MLOperand zeroPoint,
                             optional MLOperatorOptions options = {});
};

dictionary MLQuantizeDequantizeLinearSupportLimits {
  MLTensorLimits input;
  MLTensorLimits scale;
  MLTensorLimits zeroPoint;
  MLTensorLimits output;
};

partial dictionary MLOpSupportLimits {
  MLQuantizeDequantizeLinearSupportLimits dequantizeLinear;
};
参数:

返回:一个 MLOperand。 包含反量化值的输出张量。

dequantizeLinear() 的张量限制
操作数 允许的 数据类型 允许的秩
input "uint8", "int8", "uint32", "int32" N
scale "float32", "float16" input 相同
zeroPoint input 相同 input 相同
output scale 相同 input 相同

MLQuantizeDequantizeLinearSupportLimits 具有以下成员:

input类型为 MLTensorLimits

用于 input 操作数的 MLTensorLimits

scale类型为 MLTensorLimits

用于 scale 操作数的 MLTensorLimits

zeroPoint 类型为 MLTensorLimits

用于 zeroPoint 操作数的 MLTensorLimits

output类型为 MLTensorLimits

用于 output 操作数的 MLTensorLimits

MLOpSupportLimits 具有以下用于 dequantizeLinear() 的成员:

dequantizeLinear 类型为 MLQuantizeDequantizeLinearSupportLimits

运算符 dequantizeLinear() 的支持限制。

dequantizeLinear(input, scale, zeroPoint, options) 方法步骤为:
  1. 如果 this.[[hasBuilt]] 为 true,则抛出一个 "InvalidStateError" DOMException

  2. 如果以 验证操作数处理 this 以及 inputscalezeroPoint 中的任一项返回 false,则抛出一个 TypeError

  3. 如果 inputdataType 不是其允许的数据类型之一 (根据此表),则抛出一个 TypeError

  4. 如果 scaledataType 不是其允许的数据类型之一 (根据此表),则抛出一个 TypeError

  5. 如果 zeroPointdataType 不是其允许的数据类型之一 (根据此表),则抛出一个 TypeError

  6. 如果 zeroPointdataType 不等于 inputdataType,则抛出一个 TypeError

  7. 如果 scalezeroPoint不等于 input,则抛出一个 TypeError

  8. 如果 scaleshape等于 zeroPointshape,则抛出一个 TypeError

  9. 如果对 scaleshapeinputshape 进行按块广播返回 false,则抛出一个 TypeError

  10. 如果对 zeroPointshapeinputshape 进行按块广播返回 false,则抛出一个 TypeError

  11. outputDescriptor 为给定 scaledataTypeinputshape创建 MLOperandDescriptor的结果。

  12. 建立图连接:

    1. output 为给定 thisoutputDescriptor创建 MLOperand的结果。

    2. operator 为给定 inputscalezeroPointoptions 时用于 "dequantizeLinear" 操作的一个运算符

    3. output.[[operator]] 设置为 operator

    4. operator输入设置为 input

    5. operator输出设置为 output

  13. 返回 output

该操作的行为可以按如下方式由其他操作的使用进行通用仿真,尽管用户代理通常具有更高效的实现。 在底层平台不直接支持某个操作的情况下,这种分解可用作指导实现的模板。
function dequantizeLinear(builder, input, scale, zeroPoint, options) {
  // output = (input - zeroPoint) * scale
  const floatInput = builder.cast(input, scale.dataType);
  const floatZeroPoint = builder.cast(zeroPoint, scale.dataType);
  const upsampledScale = blockwiseExpand(builder, scale, input.shape);
  const upsampledZeroPoint =
    blockwiseExpand(builder, floatZeroPoint, input.shape);
  return builder.mul(
    builder.sub(floatInput, upsampledZeroPoint), upsampledScale);
}

function blockwiseExpand(builder, input, outputShape) {
  // Given the original input and a desired output shape, this expands each axis
  // by repeating the block the number of times per that axis. Though, backend
  // implementations might have much more efficient upsampling operators that
  // can accept multiple dimensions to upsample all dimensions at once by
  // integer multiples (like tile) using nearest neighbor resampling:
  // output = resample(scale, {sizes: input.shape})

  let output = input;

  for (let axis = 0; axis < input.shape.length; ++axis) {
    const oldShape = output.shape;
    const oldDimensionLength = oldShape[axis];
    const newDimensionLength = outputShape[axis];

    if (newDimensionLength != oldDimensionLength) {
      // Since tile/expand can only accept repetitions of entire dimension
      // slices (not repeating individual elements along an axis), temporarily
      // reshape the tensor to enable them to broadcast the elements up to the
      // full block size, utilizing an inserted dimension of size 1.
      const elementRepeatCount = newDimensionLength / oldDimensionLength;
      const flattenedShape = getFlattenedShapeAroundAxis(oldShape, axis);
      const unexpandedShape =
        [flattenedShape[0], flattenedShape[1], 1, flattenedShape[2]];
      const expandedShape = [
        flattenedShape[0],
        flattenedShape[1],
        elementRepeatCount,
        flattenedShape[2]
      ];
      const reshapedInput = builder.reshape(output, unexpandedShape);
      output = builder.expand(reshapedInput, expandedShape);

      let newShape = [...oldShape];
      newShape[axis] = newDimensionLength;
      output = builder.reshape(output, newShape);
    }
  }

  return output;
}

// Compute the flattened shape before and after the given axis, yielding a
// 3-element list: e.g.
// - inputShape = [2,3,4,5,6] with axis = 2 yields shape [6,4,30].
// - inputShape = [4] with axis = 0 yields shape [1,4,1].
function getFlattenedShapeAroundAxis(inputShape, axis) {
  axis = Math.max(Math.min(axis, inputShape.length - 1), 0);
  const shapeBefore = inputShape.slice(0, axis);
  const shapeAfter = inputShape.slice(axis + 1, inputShape.length);
  const countBefore = shapeBefore.reduce((a, b) => a * b, 1);
  const countAfter = shapeAfter.reduce((a, b) => a * b, 1);
  return [countBefore, inputShape[axis], countAfter];
}

8.9.17. quantizeLinear

使用 scale 和 zero-point 偏置将浮点张量量化为整数张量(例如,对于 "uint8", output = clamp(roundEven(input / scale) + zeroPoint, 0, 255))。scalezeroPoint 张量可以小于 input 张量,因为它们会被按块广播
partial interface MLGraphBuilder {
  MLOperand quantizeLinear(MLOperand input,
                           MLOperand scale,
                           MLOperand zeroPoint,
                           optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLQuantizeDequantizeLinearSupportLimits quantizeLinear;
};
参数:

返回:一个 MLOperand。 包含量化值的输出张量。

quantizeLinear() 的张量限制
操作数 允许的 数据类型 允许的秩
input "float32", "float16" N
scale input 相同 input 相同
zeroPoint "uint8", "int8", "uint32", "int32" input 相同
output zeroPoint 相同 input 相同

MLOpSupportLimits 具有以下用于 quantizeLinear() 的成员:

quantizeLinear 类型为 MLQuantizeDequantizeLinearSupportLimits

运算符 quantizeLinear() 的支持限制。

quantizeLinear(input, scale, zeroPoint, options) 方法步骤为:
  1. 如果 this.[[hasBuilt]] 为 true,则抛出一个 "InvalidStateError" DOMException

  2. 如果以 验证操作数处理 this 以及 inputscalezeroPoint 中的任一项返回 false,则抛出一个 TypeError

  3. 如果 inputdataType 不是其允许的数据类型之一 (根据此表),则抛出一个 TypeError

  4. 如果 scaledataType 不是其允许的数据类型之一 (根据此表),则抛出一个 TypeError

  5. 如果 scaledataType 不等于 inputdataType,则抛出一个 TypeError

  6. 如果 zeroPointdataType 不是其允许的数据类型之一 (根据此表),则抛出一个 TypeError

  7. 如果 scalezeroPoint不等于 input,则抛出一个 TypeError

  8. 如果 scaleshape等于 zeroPointshape,则抛出一个 TypeError

  9. 如果对 scaleshapeinputshape 进行按块广播返回 false,则抛出一个 TypeError

  10. 如果对 zeroPointshapeinputshape 进行按块广播返回 false,则抛出一个 TypeError

  11. outputDescriptor 为给定 zeroPointdataTypeinputshape创建 MLOperandDescriptor的结果。

  12. 建立图连接:

    1. output 为给定 thisoutputDescriptor创建 MLOperand的结果。

    2. operator 为给定 inputscalezeroPointoptions 时用于 "quantizeLinear" 操作的一个运算符

    3. output.[[operator]] 设置为 operator

    4. operator输入设置为 input

    5. operator输出设置为 output

  13. 返回 output

该操作的行为可以按如下方式由其他操作的使用进行通用仿真,尽管用户代理通常具有更高效的实现。 在底层平台不直接支持某个操作的情况下,这种分解可用作指导实现的模板。
function quantizeLinear(builder, input, scale, zeroPoint, options) {
  // output = clamp(roundEven(input / scale) + zeroPoint, 0, 255)
  // Note blockwiseExpand is defined in dequantizeLinear.

  const floatZeroPoint = builder.cast(zeroPoint, scale.dataType);
  const upsampledScale = blockwiseExpand(builder, scale, input.shape);
  const upsampledZeroPoint =
    blockwiseExpand(builder, floatZeroPoint, input.shape);
  const quantizedInput = builder.roundEven(builder.div(input, upsampledScale));
  const zeroPointAdjustedInput =
    builder.add(quantizedInput, upsampledZeroPoint);
  const clampedInput =
    builder.clamp(zeroPointAdjustedInput, {'minValue': 0, 'maxValue': 255});
  return builder.cast(clampedInput, zeroPoint.dataType);
}

8.9.18. elu

对输入张量逐元素计算指数线性单元函数 (ELU)。计算遵循表达式 max(0, x) + alpha * (exp(min(0, x)) - 1)
dictionary MLEluOptions : MLOperatorOptions {
  double alpha = 1;
};

partial interface MLGraphBuilder {
  MLOperand elu(MLOperand input, optional MLEluOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits elu;
};

MLEluOptions 具有以下成员:

alpha类型为 double,默认为 1

标量乘数。

参数:

返回:

elu() 的张量限制
操作数 允许的 数据类型 允许的秩
input "float32", "float16" N
output input 相同 input 相同

MLOpSupportLimits 具有以下用于 elu() 的成员:

elu类型为 MLSingleInputSupportLimits

运算符 elu() 的支持限制。

elu(input, options) 方法 步骤为:
  1. 如果 this 不可构建,则抛出一个 "InvalidStateError" DOMException

  2. 如果以 验证操作数处理 thisinput 返回 false,则抛出一个 TypeError

  3. 如果 inputdataType 不是其允许的数据类型之一 (根据此表),则抛出一个 TypeError

  4. options.alpha 设置为将 options.alpha 转换inputdataType 的结果。

  5. 建立图连接:

    1. output 为给定 input复制 MLOperand的结果。

    2. operator 为给定 options 时用于 "elu" 操作的一个运算符

    3. output.[[operator]] 设置为 operator

    4. operator输入设置为 input

    5. operator输出设置为 output

  6. 返回 output

该操作的行为可以按如下方式由其他操作的使用进行通用仿真,尽管用户代理通常具有更高效的实现。 在底层平台不直接支持某个操作的情况下,这种分解可用作指导实现的模板。
function elu(builder, input, options) {
  return builder.add(
    builder.max(builder.constant(input.dataType, 0), input),
    builder.mul(
      builder.constant(input.dataType, options.alpha),
      builder.sub(
        builder.exp(builder.min(builder.constant(input.dataType, 0), input)),
        builder.constant(input.dataType, 1))));
}

8.9.19. expand

新しい形状に従って、入力テンソルのサイズ1の任意の次元をより大きなサイズへ拡張する。この拡張は [numpy-broadcasting-rule]と一貫している。入力テンソルは新しい形状へ単方向ブロードキャスト可能でなければならない。各 次元はサイズ1であるか、新しい形状に従って対応する出力次元のサイズと一致しなければならない。
partial interface MLGraphBuilder {
  MLOperand expand(MLOperand input,
                   sequence<[EnforceRange] unsigned long> newShape,
                   optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits expand;
};
引数:

戻り値: MLOperand。 サイズ形状が拡張されたテンソル。

expand()のテンソル制限
オペランド 許可される データ型 許可されるランク
input 任意 N
output input同じ N

MLOpSupportLimitsexpand()について次のメンバーを持つ。

expand, 型はMLSingleInputSupportLimits

expand()演算子のサポート制限。

expand(input, newShape, options) メソッドの手順は次のとおりである。
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. outputShapeを、inputshapeおよびnewShape単方向ブロードキャストする結果とする。

    1. それがfailureを返す場合、TypeErrorthrowする。

  4. outputShapesizeが (この表に従う)出力テンソルの許可されるランクでない場合、TypeErrorthrowする。

  5. outputDescriptorを、inputdataTypeおよび outputShapeが与えられてMLOperandDescriptorを 作成する結果とする。

  6. グラフ接続を作成する:

    1. outputを、thisおよび outputDescriptorが与えられてMLOperandを 作成する結果とする。

    2. operatorを、inputnewShape、およびoptionsが 与えられた"expand"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. operatoroutputoutputに設定する。

  7. outputを返す。

8.9.20. gather

indicesに従って、軸に沿って入力テンソルの値を収集する。
dictionary MLGatherOptions : MLOperatorOptions {
  [EnforceRange] unsigned long axis = 0;
};

partial interface MLGraphBuilder {
  MLOperand gather(MLOperand input,
                   MLOperand indices,
                   optional MLGatherOptions options = {});
};

dictionary MLGatherSupportLimits {
  MLTensorLimits input;
  MLTensorLimits indices;
  MLTensorLimits output;
};

partial dictionary MLOpSupportLimits {
  MLGatherSupportLimits gather;
};

MLGatherOptions は次のメンバーを持つ。

axis, 型はunsigned long、デフォルトは0

収集される値を取得する軸。その値は、入力テンソルのrankをNとすると、[0, N-1]の範囲内でなければならない。

引数:

戻り値: MLOperandrankinputrank + indicesrank - 1に等しい出力N-Dテンソル。

indices パラメーターは、グラフが構築される時点では入力が実行まで不明であるため、gather() に対して許可範囲にクランプできない。指定されたクランプ動作が基盤となるプラットフォームによって提供されない場合、 実装はコンパイル済みグラフ内にclamp() を導入できる。同様に、基盤となるプラットフォームが負のインデックスをサポートしない場合、実装はコンパイル済み グラフ内に、次元の末尾からの負のインデックスを正のインデックスへ変換する演算を導入できる。
gather()のテンソル制限
オペランド 許可される データ型 許可されるランク
input 任意 1からNまで
indices "int32", "uint32", "int64" N
output input同じ N

MLGatherSupportLimits は次のメンバーを持つ。

input, 型はMLTensorLimits

inputオペランド用のMLTensorLimits

indices, 型はMLTensorLimits

indicesオペランド用のMLTensorLimits

output, 型はMLTensorLimits

outputオペランド用のMLTensorLimits

MLOpSupportLimitsgather()について次のメンバーを持つ。

gather, 型はMLGatherSupportLimits

gather()演算子のサポート制限。

gather(input, indices, options) メソッドの手順は次のとおりである。
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputindicesのいずれかとともに行った 結果がfalseを返す場合、TypeErrorthrowする。

  3. indicesdataTypeが(この表に従う)その許可されるデータ型の いずれでもない場合、TypeErrorthrowする。

  4. inputShapeinputshapeとし、inputRankinputrankとする。

  5. indicesShapeindicesshapeとする。

  6. axisoptions.axisとする。

  7. axisinputRank以上である場合、TypeErrorthrowする。

  8. dimCountをゼロとする。

  9. outputRankをゼロとする。

  10. outputShapeを空のリストとする。

  11. inputShapeの各sizeについて実行する:

    1. dimCountaxisと等しい場合、breakする。

    2. outputShape[dimCount]をsizeに設定する。

    3. dimCountを1増やす。

  12. outputRankdimCountに設定する。

  13. dimCountをゼロとする。

  14. indicesShapeの各sizeについて実行する:

    1. outputShape[outputRank + dimCount]を sizeに設定する。

    2. dimCountを1増やす。

  15. outputRankoutputRank + dimCountに設定する。

  16. dimCountをゼロとする。

  17. inputShapeの各sizeについて実行する:

    1. dimCountaxis以下である場合、continueする。

    2. outputShape[outputRank + dimCount - axis - 1]をsizeに設定する。

    3. dimCountを1増やす。

  18. descを、inputdataTypeおよび outputShapeが与えられてMLOperandDescriptorを 作成する結果とする。

  19. グラフ接続を作成する:

    1. outputを、descが与えられてMLOperandを 作成する結果とする。

    2. operatorを、inputindices、およびoptionsが 与えられた"gather"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputsinputおよびindicesに 設定する。

    5. operatoroutputoutputに設定する。

  20. outputを返す。

異なるスライス方式でgatherがどのように動作するかの例。
// input of shape [4,3]:
//   [[ 0,  1,  2],
//    [10, 11, 12],
//    [20, 21, 22],
//    [30, 31, 32]]
const input = builder.constant(
  {dataType: 'float32', shape: [4, 3]},
  new Float32Array([0, 1, 2, 10, 11, 12, 20, 21, 22, 30, 31, 32]));

// axis = 0 (default)
// indices of shape [2]:
//   [3,1]
// output of shape [2,3]:
//   [[30, 31, 32],
//    [10, 11, 12]]

const indices1 =
  builder.constant({dataType: 'uint32', shape: [2]}, new Uint32Array([3, 1]));

const output1 = builder.gather(input, indices1);

// axis = 1
// indices of shape [3]:
//   [2,1,1]
// output of shape [4,3]:
//   [[ 2,  1,  1],
//    [12, 11, 11],
//    [22, 21, 21],
//    [32, 31, 31]]

const indices2 = builder.constant(
  {dataType: 'uint32', shape: [3]}, new Uint32Array([2, 1, 1]));

const output2 = builder.gather(input, indices2, {axis: 1});

// axis = 1
// indices of shape [2,2]:
//   [[0, 1],
//    [1, 2]]
// output of shape [4,2,2]:
//   [[[ 0,  1], [ 1,  2]],
//    [[10, 11], [11, 12]],
//    [[20, 21], [21, 22]],
//    [[30, 31], [31, 32]]]

const indices3 = builder.constant(
  {dataType: 'uint32', shape: [2, 2]}, new Uint32Array([0, 1, 1, 2]));

const output3 = builder.gather(input, indices3, {axis: 1});

8.9.21. gatherElements

indicesに従って、軸に沿って入力テンソルの値を収集する。
partial interface MLGraphBuilder {
  MLOperand gatherElements(MLOperand input,
                           MLOperand indices,
                           optional MLGatherOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLGatherSupportLimits gatherElements;
};
引数:

戻り値: MLOperandrankinputrankと等しい出力N-Dテンソル。

gatherElements()のテンソル制限
オペランド 許可される データ型 許可されるランク
input 任意 1からNまで
indices "int32", "uint32", "int64" input同じ
output input同じ input同じ

MLOpSupportLimitsgatherElements()について次のメンバーを持つ。

gatherElements, 型は MLGatherSupportLimits

gatherElements()演算子のサポート制限。

indices パラメーターは、グラフが構築される時点では入力が実行まで不明であるため、gatherElements() に対して許可範囲にクランプできない。指定されたクランプ動作が基盤となるプラットフォームによって提供されない場合、 実装はコンパイル済みグラフ内にclamp() を導入できる。同様に、基盤となるプラットフォームが負のインデックスをサポートしない場合、実装はコンパイル済み グラフ内に、次元の末尾からの負のインデックスを正のインデックスへ変換する演算を導入できる。
gatherElements(input, indices, options) メソッドの手順は次のとおりである。
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputindicesのいずれかとともに行った 結果がfalseを返す場合、TypeErrorthrowする。

  3. indicesdataTypeが(この表に従う)その許可されるデータ型の いずれでもない場合、TypeErrorthrowする。

  4. inputまたはindicesのいずれかのrankが、その許可されるランクでない場合、TypeErrorthrowする。

  5. axisoptions.axisとする。

  6. axisinputrank以上である場合、TypeErrorthrowする。

  7. indicesShapeExpectedinputshapeのコピーとする。

  8. indicesShapeExpected[axis]をindicesshape[axis]に設定する。

  9. indicesshapeindicesShapeExpectedと等しくない場合、 TypeErrorthrowする。

  10. グラフ接続を作成する:

    1. outputを、inputが与えられてMLOperandをコピーする結果とする。

    2. operatorを、inputindices、およびoptionsが 与えられた"gatherElements"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputsinputおよびindicesに 設定する。

    5. operatoroutputoutputに設定する。

  11. outputを返す。

異なるスライス方式でgatherElementsがどのように動作するかの例。
// input of shape [4,3]:
//   [[ 0,  1,  2],
//    [10, 11, 12],
//    [20, 21, 22],
//    [30, 31, 32]]
// indices of shape [2,3]:
//   [[3, 1, 1],
//    [2, 0, 3]]
// axis = 0 (default)
// output of shape [2,3]:
//   [[30, 11, 12],
//    [20,  1, 32]]

const input1 = builder.constant(
  {dataType: 'float32', shape: [4, 3]},
  new Float32Array([0, 1, 2, 10, 11, 12, 20, 21, 22, 30, 31, 32]));

const indices1 = builder.constant(
  {dataType: 'uint32', shape: [2, 3]}, new Uint32Array([3, 1, 1, 2, 0, 3]));

const output1 = builder.gatherElements(input1, indices1);

// input of shape [4,3]:
//   [[ 0,  1,  2],
//    [10, 11, 12],
//    [20, 21, 22],
//    [30, 31, 32]]
// indices of shape [4,1]:
//   [[2],
//    [1],
//    [0],
//    [2]],
// axis = 1
// output of shape [4,1]:
//   [[ 2],
//    [11],
//    [20],
//    [32]]

const indices2 = builder.constant(
  {dataType: 'uint32', shape: [4, 1]}, new Uint32Array([2, 1, 0, 2]));

const output2 = builder.gatherElements(input1, indices2, {axis: 1});

// input of shape [4,2,2]:
//   [[[  0,   1],
//     [ 10,  11]],
//    [[100, 101],
//     [110, 111]],
//    [[200, 201],
//     [210, 211]],
//    [[300, 301],
//     [310, 311]],]
// indices of shape [1,2,2]:
//   [[[0, 2],
//     [1, 3]]],
// axis = 0
// output of shape [1,2,2]:
//   [[[  0, 201],
//     [110, 311]]]

const inputData3 = new Float32Array(
  [0, 1, 10, 11, 100, 101, 110, 111, 200, 201, 210, 211, 300, 301, 310, 311]);

const input3 =
  builder.constant({dataType: 'float32', shape: [4, 2, 2]}, inputData3);

const indices3 = builder.constant(
  {dataType: 'uint32', shape: [1, 2, 2]}, new Uint32Array([0, 2, 1, 3]));

const output3 = builder.gatherElements(input3, indices3, {axis: 0});

8.9.22. gatherND

indicesに従って、入力テンソルのスライスを収集する。
partial interface MLGraphBuilder {
  MLOperand gatherND(MLOperand input,
                     MLOperand indices,
                     optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLGatherSupportLimits gatherND;
};
引数:

戻り値: MLOperandrankinputrank + indicesrank - indicesshape[-1] - 1に等しい 出力N-Dテンソル。

gatherND()のテンソル制限
オペランド 許可される データ型 許可されるランク
input 任意 1からNまで
indices "int32", "uint32", "int64" 1からNまで
output input同じ N

MLOpSupportLimitsgatherND()について次のメンバーを持つ。

gatherND, 型はMLGatherSupportLimits

gatherND()演算子のサポート制限。

indices パラメーターは、グラフが構築される時点では入力が実行まで不明であるため、gatherND() に対して許可範囲にクランプできない。指定されたクランプ動作が基盤となるプラットフォームによって提供されない場合、 実装はコンパイル済みグラフ内にclamp() を導入できる。同様に、基盤となるプラットフォームが負のインデックスをサポートしない場合、実装はコンパイル済み グラフ内に、次元の末尾からの負のインデックスを正のインデックスへ変換する演算を導入できる。
gatherND(input, indices, options) メソッドの手順は次のとおりである。
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputindicesのいずれかとともに行った 結果がfalseを返す場合、TypeErrorthrowする。

  3. indicesdataTypeが(この表に従う)許可されるデータ型の いずれでもない場合、TypeErrorthrowする。

  4. inputまたはindicesのいずれかのrankが、その許可されるランクでない場合、TypeErrorthrowする。

  5. inputShapeinputshapeとし、inputRankinputrankとする。

  6. indicesShapeindicesshapeとし、indicesRankindicesrankとする。

  7. inputまたはindicesのいずれかのrankが、その許可されるランクでない場合、TypeErrorthrowする。

  8. indexableSizeindicesRank - 1とする。

  9. coordinateSizeindicesShape[indexableSize]とする。

  10. coordinateSizeinputRankより大きい場合、TypeErrorthrowする。

  11. outputShapeを空のリストとする。

  12. 0からindexableSizeまで(含まない)の範囲内の各indexについて実行する:

    1. indicesShape[index]をoutputShapeappendする。

  13. coordinateSizeからinputRankまで(含まない)の範囲内の各indexについて実行する:

    1. inputShape[index]をoutputShapeappendする。

  14. outputDescを、inputdataTypeおよび outputShapeが与えられてMLOperandDescriptorを 作成する結果とする。

  15. グラフ接続を作成する:

    1. outputを、outputDescが与えられてMLOperandを 作成する結果とする。

    2. operatorを、inputindices、およびoptionsが 与えられた"gatherND"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputsinputおよびindicesに 設定する。

    5. operatoroutputoutputに設定する。

  16. outputを返す。

異なるスライス方式でgatherNDがどのように動作するかの例。
// input of shape [2,2]:
//   [[0, 1],
//    [2, 3]]
// indices of shape [3,2]:
//   [[0, 0],
//    [1, 1],
//    [1, 0]]
// output of shape [3]:
//   [0, 3, 2]

const input1 = builder.constant(
  {dataType: 'float32', shape: [2, 2]}, new Float32Array([0, 1, 2, 3]));

const indices1 = builder.constant(
  {dataType: 'uint32', shape: [3, 2]}, new Uint32Array([0, 0, 1, 1, 1, 0]));

const output1 = builder.gatherND(input1, indices1);

// input of shape [2,2]:
//   [[0, 1],
//    [2, 3]]
// indices of shape [2,1]:
//   [[1],
//    [0]]
// output of shape [2,2]:
//   [[2, 3]    <= row [2, 3] from input coordinates [1, *]
//    [0, 1]]   <= row [0, 1] from input coordinates [0, *]

const indices2 = builder.constant(
  {dataType: 'uint32', shape: [2, 1]}, new Uint32Array([1, 0]));

const output2 = builder.gatherND(input1, indices2);

// input of shape [2,2,2]:
//   [[[0, 1],
//     [2, 3]],
//    [[4, 5],
//     [6, 7]]]
// indices of shape [2,2]:
//   [[0, 1],
//    [1, 0]]
// output of shape [2,2]:
//   [[2, 3],   <= row [2, 3] from input coordinates [0, 1, *]
//    [4, 5]]   <= row [4, 5] from input coordinates [1, 0, *]

const input2 = builder.constant(
  {dataType: 'float32', shape: [2, 2, 2]},
  new Float32Array([0, 1, 2, 3, 4, 5, 6, 7]));

const indices3 = builder.constant(
  {dataType: 'uint32', shape: [2, 2]}, new Uint32Array([0, 1, 1, 0]));

const output3 = builder.gatherND(input2, indices3);

// input of shape [2,2,2]:
//   [[[0, 1],
//     [2, 3]],
//    [[4, 5],
//     [6, 7]]]
// indices of shape [3,1]:
//   [[1],
//    [0],
//    [1]]
// output of shape [3,2,2]:
//   [[[4, 5],   <= block [[4, 5], [6, 7]] from input coordinates [1, *, *]
//     [6, 7]],
//    [[0, 1],   <= block [[0, 1], [2, 3]] from input coordinates [0, *, *]
//     [2, 3]],
//    [[4, 5],   <= block [[4, 5], [6, 7]] from input coordinates [1, *, *]
//     [6, 7]]]

const indices4 = builder.constant(
  {dataType: 'uint32', shape: [3, 1]}, new Uint32Array([1, 0, 1]));

const output4 = builder.gatherND(input2, indices4);

// input of shape [2,2,2]:
//   [[[0, 1],
//     [2, 3]],
//    [[4, 5],
//     [6, 7]]]
// indices of shape [5,3]:
//   [[0,0,1],
//    [0,1,0],
//    [1,0,0],
//    [1,1,0],
//    [1,1,1]]
// output of shape [5]:
//   [1,2,4,6,7]

const indices5 = builder.constant(
  {dataType: 'uint32', shape: [5, 3]},
  new Uint32Array([0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 1, 1, 1]));

const output5 = builder.gatherND(input2, indices5);

8.9.23. gelu

入力テンソルのガウス 誤差線形ユニット関数(GELU)を計算する。計算は式 0.5 * x * (1 + erf(x / sqrt(2)))に従う。
partial interface MLGraphBuilder {
  MLOperand gelu(MLOperand input, optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits gelu;
};
引数:

戻り値:

gelu()のテンソル制限
オペランド 許可される データ型 許可されるランク
input "float32", "float16" N
output input同じ input同じ

MLOpSupportLimitsgelu()について次のメンバーを持つ:

gelu, 型はMLSingleInputSupportLimits

gelu()演算子のサポート制限。

gelu(input, options)メソッドの 手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. inputdataTypeが(この表に従う)その許可されるデータ型の いずれでもない場合、TypeErrorthrowする。

  4. グラフ接続を作成する:

    1. outputを、inputが与えられてMLOperandをコピーする結果とする。

    2. operatorを、optionsが与えられた"gelu"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. operatoroutputoutputに設定する。

  5. outputを返す。

この演算の振る舞いは、ユーザーエージェントは通常より効率的な実装を持つものの、次のように他の演算の使用から 一般的にエミュレートできる。基盤となるプラットフォームが演算を直接サポートしない場合、この分解は 実装を導くためのテンプレートとして使用できる。
function gelu(builder, input) {
  return builder.mul(
    builder.mul(input, builder.constant(input.dataType, 0.5)),
    builder.add(
      builder.constant(input.dataType, 1),
      builder.erf(builder.div(
        input, builder.sqrt(builder.constant(input.dataType, 2))))));
}

8.9.24. gemm

Basic Linear Algebra Subprogramsの一般行列乗算を計算する。計算は式 alpha * A * B + beta * Cに従う。ここで、Aは形状[M, K]または [K, M]を持つ2-Dテンソル、Bは形状[K, N]または[N, K]を持つ 2-Dテンソルであり、Cは形状[M, N]単方向ブロードキャスト可能である。Aおよび Bは、計算の前に任意で転置できる。
dictionary MLGemmOptions : MLOperatorOptions {
  MLOperand c;
  double alpha = 1.0;
  double beta = 1.0;
  boolean aTranspose = false;
  boolean bTranspose = false;
};

partial interface MLGraphBuilder {
  MLOperand gemm(MLOperand a, MLOperand b, optional MLGemmOptions options = {});
};

dictionary MLGemmSupportLimits {
  MLTensorLimits a;
  MLTensorLimits b;
  MLTensorLimits c;
  MLTensorLimits output;
};

partial dictionary MLOpSupportLimits {
  MLGemmSupportLimits gemm;
};

MLGemmOptions は次のメンバーを持つ:

c, 型はMLOperand

第3入力テンソル。これはスカラー、または形状[M, N]単方向ブロードキャスト可能な形状である。 指定されない場合、計算はc がスカラー0.0であるかのように行われる。

alpha, 型はdouble、デフォルトは1.0

第1入力用の乗数。

beta, 型はdouble、デフォルトは1.0

第3入力c用の乗数。

aTranspose, 型はboolean、デフォルトはfalse

出力を計算する前に第1入力を転置するかを示す。

bTranspose, 型はboolean、デフォルトはfalse

出力を計算する前に第2入力を転置するかを示す。

引数:

戻り値: MLOperand。 すべての入力の計算された積を含む、形状[M, N]の出力2-Dテンソル。

gemm()のテンソル制限
オペランド 許可される データ型 許可されるランク
a "float32", "float16" 2
b a同じ 2
c a同じ 0から2
output a同じ 2

MLGemmSupportLimits は次のメンバーを持つ:

a, 型はMLTensorLimits

aオペランド用のMLTensorLimits

b, 型はMLTensorLimits

bオペランド用のMLTensorLimits

c, 型はMLTensorLimits

cオペランド用のMLTensorLimits

output, 型はMLTensorLimits

outputオペランド用のMLTensorLimits

MLOpSupportLimitsgemm()について次のメンバーを持つ:

gemm, 型はMLGemmSupportLimits

gemm()演算子のサポート制限。

gemm(a, b, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびabのいずれかとともに行った結果がfalseを返す場合、 TypeErrorthrowする。

  3. aまたはbのいずれかのdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

  4. aまたはbのいずれかのrankが、その許可されるランクでない場合、TypeErrorthrowする。

  5. options.alpha を、options.alphaadataTypeキャストする結果に設定する。

  6. options.beta を、options.betaadataTypeキャストする結果に設定する。

  7. shapeAを、ashapecloneとする。

  8. shapeBを、bshapecloneとする。

  9. options.aTranspose がtrueの場合、shapeA内のitemsの順序を反転する。

  10. options.bTranspose がtrueの場合、shapeB内のitemsの順序を反転する。

  11. shapeA[1]がshapeB[0]と等しくない場合、TypeErrorthrowする。

  12. options.c存在する場合:

    1. それが形状« shapeA[0], shapeB[1] »へ単方向ブロードキャスト可能でない場合、TypeErrorthrowする。

    2. そのdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

  13. descを、adataTypeおよび« shapeA[0], shapeB[1] »が与えられてMLOperandDescriptorを作成する結果とする。

  14. グラフ接続を作成する:

    1. outputを、thisおよび descが与えられてMLOperandを作成する結果とする。

    2. operatorを、optionsが与えられた"gemm"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputsaおよびbに設定する。

    5. options.c存在する場合、それをoperatorinputsに追加する。

    6. operatoroutputoutputに設定する。

  15. outputを返す。

この演算の振る舞いは、ユーザーエージェントは通常より効率的な実装を持つものの、次のように他の演算の使用から 一般的にエミュレートできる。基盤となるプラットフォームが演算を直接サポートしない場合、この分解は 実装を導くためのテンプレートとして使用できる。
function gemm(builder, a, b, options) {
  if (options.aTranspose)
    a = builder.transpose(a);

  if (options.bTranspose)
    b = builder.transpose(b);

  let ab = builder.matmul(
    builder.mul(builder.constant(a.dataType, options.alpha), a), b);
  return (
    options.c ?
      builder.add(
        ab,
        builder.mul(builder.constant(a.dataType, options.beta), options.c)) :
      ab);
}

8.9.25. gru

Gated Recurrent Unit [GRU] recurrent networkは、update、reset、およびnew gateを使用して、ネットワークの時間的シーケンスにわたって 出力へ繰り込まれる出力状態を計算する。
enum MLGruWeightLayout {
  "zrn",  // update-reset-new gate ordering
  "rzn"   // reset-update-new gate ordering
};

enum MLRecurrentNetworkActivation {
  "relu",
  "sigmoid",
  "tanh"
};

enum MLRecurrentNetworkDirection {
  "forward",
  "backward",
  "both"
};

dictionary MLGruOptions : MLOperatorOptions {
  MLOperand bias;
  MLOperand recurrentBias;
  MLOperand initialHiddenState;
  boolean resetAfter = true;
  boolean returnSequence = false;
  MLRecurrentNetworkDirection direction = "forward";
  MLGruWeightLayout layout = "zrn";
  sequence<MLRecurrentNetworkActivation> activations;
};

partial interface MLGraphBuilder {
  sequence<MLOperand> gru(MLOperand input,
                          MLOperand weight,
                          MLOperand recurrentWeight,
                          [EnforceRange] unsigned long steps,
                          [EnforceRange] unsigned long hiddenSize,
                          optional MLGruOptions options = {});
};

dictionary MLGruSupportLimits {
  MLTensorLimits input;
  MLTensorLimits weight;
  MLTensorLimits recurrentWeight;
  MLTensorLimits bias;
  MLTensorLimits recurrentBias;
  MLTensorLimits initialHiddenState;
  MLTensorLimits output0;
  MLTensorLimits output1;
};

partial dictionary MLOpSupportLimits {
  MLGruSupportLimits gru;
};

MLGruOptions は次のメンバーを持つ:

bias, 型はMLOperand

形状[numDirections, 3 * hiddenSize]の2-D入力バイアステンソル。テンソル形状の第2次元における バイアスベクトルの順序は、layoutに従って指定される。

recurrentBias, 型はMLOperand

形状[numDirections, 3 * hiddenSize]の2-D再帰バイアステンソル。テンソル形状の第2次元における バイアスベクトルの順序は、layoutに従って指定される。

initialHiddenState, 型はMLOperand

形状[numDirections, batchSize, hiddenSize]の3-D初期隠れ状態テンソル。 指定されない場合、実装はゼロで埋められたテンソルを使用しなければならない。

resetAfter, 型はboolean、デフォルトはtrue

行列乗算の後または前にreset gateを適用するかを示す。

returnSequence, 型は boolean、デフォルトはfalse

最後のtime stepの出力に加えて、各time stepからのすべての出力を含むシーケンス全体も返すかを示す。

direction, 型はMLRecurrentNetworkDirection、デフォルトは "forward"

入力シーケンスの処理方向。"both"に 設定された場合、weightおよびbiasテンソル形状の第1次元のサイズは2でなければならず、入力は 両方向で処理される。

layout, 型はMLGruWeightLayout、デフォルトは "zrn"

GRUの内部gate、具体的にはupdate (z)reset (r)、および new (n) gateに対するweightおよびbiasベクトルの順序。weightおよびbiasテンソル形状の 第2次元で示される。

activations, 型は sequence<MLRecurrentNetworkActivation>

活性化関数のペアを指定する。第1の関数はupdateおよびreset gateに 使用され、第2の関数はnew gateに使用される。指定されない場合、それぞれ"sigmoid" および"tanh" 関数がデフォルトとなる。

引数:

戻り値: sequence<MLOperand>。 第1要素は、形状[numDirections, batchSize, hiddenSize]の3-Dテンソルであり、ネットワークの 最後のtime stepからのcell出力である。さらに、returnSequence がtrueに設定されている場合、第2要素は時間的シーケンス内の各time stepからのすべてのcell出力を含む 形状[steps, numDirections, batchSize, hiddenSize]の4-D出力テンソルである。

gru()のテンソル制限
オペランド 許可される データ型 許可されるランク
input "float32", "float16" 3
weight input同じ 3
recurrentWeight input同じ 3
bias input同じ 2
recurrentBias input同じ 2
initialHiddenState input同じ 3
outputs[0] input同じ 3
returnSequence がtrueの場合のoutputs[1] input同じ 4

MLGruSupportLimits は次のメンバーを持つ:

input, 型はMLTensorLimits

inputオペランド用のMLTensorLimits

weight, 型はMLTensorLimits

weightオペランド用のMLTensorLimits

recurrentWeight, 型はMLTensorLimits

recurrentWeightオペランド用のMLTensorLimits

bias, 型はMLTensorLimits

biasオペランド用のMLTensorLimits

recurrentBias, 型はMLTensorLimits

recurrentBiasオペランド用のMLTensorLimits

initialHiddenState, 型はMLTensorLimits

initialHiddenStateオペランド用のMLTensorLimits

output0, 型はMLTensorLimits

すべての出力オペランド[0]用のMLTensorLimits

output1, 型はMLTensorLimits

すべての出力オペランド[1]用のMLTensorLimits

MLOpSupportLimitsgru()について次のメンバーを持つ:

gru, 型はMLGruSupportLimits

gru()演算子のサポート制限。

gru(input, weight, recurrentWeight, steps, hiddenSize, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputweightrecurrentWeightoptions.bias (それが存在する場合)、options.recurrentBias (それが存在する場合)、およびoptions.initialHiddenState (それが存在する場合)のいずれかとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. inputweightまたはrecurrentWeightのいずれかのdataTypeが(この表に従う)その許可されるデータ型の いずれでもない場合、TypeErrorthrowする。

  4. inputweightまたはrecurrentWeightのいずれかのrankが、その許可されるランクでない場合、 TypeErrorthrowする。

  5. inputshape[0]がstepsと等しくない場合、TypeErrorthrowする。

  6. batchSizeinputshape[1]とする。

  7. inputSizeinputshape[2]とする。

  8. numDirectionsを、options.direction"both" の場合は2、そうでない場合は1とする。

  9. weightshapeが« numDirections, 3 * hiddenSize, inputSize »と等しくない場合、TypeErrorthrowする。

  10. recurrentWeightshapeが« numDirections, 3 * hiddenSize, hiddenSize »と等しくない場合、TypeErrorthrowする。

  11. hiddenSize * 6が有効な次元でない場合、TypeErrorthrowする。

    なぜhiddenSize * 6なのか? 一部の基盤となるプラットフォームは、biasrecurrentBiasを 連結した単一のバイアステンソルを操作する。そのため、3 * hiddenSize + 3 * hiddenSize有効な 次元である必要がある。
  12. options.bias存在する場合:

    1. そのdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

    2. そのshapeが« numDirections, 3 * hiddenSize »と等しくない場合、TypeErrorthrowする。

  13. options.recurrentBias存在する場合:

    1. そのdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

    2. そのshapeが« numDirections, 3 * hiddenSize »と等しくない場合、TypeErrorthrowする。

  14. options.initialHiddenState存在する場合:

    1. そのdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

    2. そのshapeが« numDirections, batchSize, hiddenSize »と等しくない場合、TypeErrorthrowする。

  15. options.activations存在する場合:

    1. そのsizeが2でない場合、TypeErrorthrowする。

    2. activationsを、options.activationsclone とする。

  16. そうでない場合:

    1. activationsを« "sigmoid", "tanh" »とする。

  17. 出力形状を計算する:

    1. desc0を、inputdataTypeおよび« numDirections, batchSize, hiddenSize »が与えられてMLOperandDescriptorを作成する結果とする。

    2. options.returnSequence がtrueの場合:

      1. desc1を、inputdataType および« steps, numDirections, batchSize, hiddenSize »が与えられてMLOperandDescriptorを作成する結果とする。

  18. グラフ接続を作成する:

    1. operatorを、weightrecurrentWeightstepshiddenSizeおよびoptionsが与えられた"gru"演算用の演算子とする。

    2. output0を、thisおよび desc0が与えられてMLOperandを作成する結果とする。

    3. options.returnSequence がtrueの場合:

      1. output1を、this およびdesc1が与えられてMLOperandを作成する結果とする。

      2. outputリスト« output0, output1 »とする。

      3. output0.[[operator]] およびoutput1.[[operator]]operatorに設定する。

    4. そうでない場合:

      1. outputリスト« output0 »とする。

      2. output0.[[operator]]operatorに設定する。

    5. operatorinputsinputweight、および recurrentWeightに設定する。

    6. options.bias存在する場合、それをoperatorinputsに追加する。

    7. options.recurrentBias存在する場合、それをoperatorinputsに追加する。

    8. options.initialHiddenState存在する場合、それをoperatorinputsに追加する。

    9. operator活性化関数を、activationscloneに設定する。

    10. operatoroutputoutputに設定する。

  19. outputを返す。

squeeze()ヘルパーを使用して、この演算の振る舞いは、ユーザーエージェントは 通常より効率的な実装を持つものの、次のように他の演算の使用から一般的にエミュレートできる。 基盤となるプラットフォームが演算を直接サポートしない場合、この分解は実装を導くためのテンプレートとして 使用できる。
function gru(
  builder, input, weight, recurrentWeight, steps, hiddenSize, options) {
  const batchSize = input.shape[1];
  const inputSize = input.shape[2];
  const direction = options.direction || 'forward';
  const numDirections = (direction == 'both' ? 2 : 1);
  let hiddenState = options.initialHiddenState;

  if (!hiddenState) {
    const desc = {
      dataType: 'float32',
      shape: [numDirections, batchSize, hiddenSize]
    };
    const totalSize = numDirections * batchSize * hiddenSize;
    hiddenState = builder.constant(desc, new Float32Array(totalSize).fill(0));
  }

  let currentWeight = [];
  let currentRecurrentWeight = [];
  let currentBias = [];
  let currentRecurrentBias = [];
  let forwardSequence = null;
  let backwardSequence = null;
  let outputHidden = null;

  for (let dir = 0; dir < numDirections; ++dir) {
    currentWeight.push(squeeze(
      builder,
      builder.slice(weight, [dir, 0, 0], [1, 3 * hiddenSize, inputSize])));
    currentRecurrentWeight.push(squeeze(
      builder,
      builder.slice(
        recurrentWeight, [dir, 0, 0], [1, 3 * hiddenSize, hiddenSize])));
    currentBias.push(
      options.bias ?
        (squeeze(
          builder,
          builder.slice(options.bias, [dir, 0], [1, 3 * hiddenSize]))) :
        null);
    currentRecurrentBias.push(
      options.recurrentBias ?
        (squeeze(
          builder,
          builder.slice(
            options.recurrentBias, [dir, 0], [1, 3 * hiddenSize]))) :
        null);
    let currentHidden = squeeze(
      builder,
      builder.slice(hiddenState, [dir, 0, 0], [1, batchSize, hiddenSize]), [0]);

    for (let step = 0; step < steps; ++step) {
      const slice =
        (dir == 1 || direction == 'backward' ? steps - step - 1 : step);
      const currentInput = squeeze(
        builder,
        builder.slice(input, [slice, 0, 0], [1, batchSize, inputSize]), [0]);

      currentHidden = builder.gruCell(
        currentInput,
        currentWeight[dir],
        currentRecurrentWeight[dir],
        currentHidden,
        hiddenSize,
        {
          bias: currentBias[dir],
          recurrentBias: currentRecurrentBias[dir],
          resetAfter: options.resetAfter,
          layout: options.layout,
          activations: options.activations
        });

      if (options.returnSequence) {
        // Expand currentHidden of 2D([batchSize, hiddenSize])
        // to 4D([steps, numDirections, batchSize, hiddenSize])
        const expandedHiddenAs4D =
          builder.reshape(currentHidden, [1, 1, batchSize, hiddenSize]);

        if (direction == 'forward' || (dir == 0 && direction == 'both')) {
          forwardSequence = forwardSequence ?
            builder.concat([forwardSequence, expandedHiddenAs4D], 0) :
            expandedHiddenAs4D;
        } else if (
          direction == 'backward' || (dir == 1 && direction == 'both')) {
          backwardSequence = backwardSequence ?
            builder.concat([expandedHiddenAs4D, backwardSequence], 0) :
            expandedHiddenAs4D;
        }
      }
    }

    // Expand currentHidden of 2D([batchSize, hiddenSize])
    // to 3D([numDirections, batchSize, hiddenSize])
    const expandedHiddenAs3D =
      builder.reshape(currentHidden, [1, batchSize, hiddenSize]);
    outputHidden = outputHidden ?
      builder.concat([outputHidden, expandedHiddenAs3D], 0) :
      expandedHiddenAs3D;
  }

  if (options.returnSequence) {
    let outputSequence = null;

    if (direction == 'forward') {
      outputSequence = forwardSequence;
    } else if (direction == 'backward') {
      outputSequence = backwardSequence;
    } else if (direction == 'both') {
      // Concat along axis 1 (numDirections dimension)
      outputSequence = builder.concat([forwardSequence, backwardSequence], 1);
    }

    return [outputHidden, outputSequence];
  } else {
    return [outputHidden];
  }
}

8.9.26. gruCell

Gated Recurrent Unit [GRU] recurrent networkの単一time stepであり、update gateおよびreset gateを使用して、recurrent networkの時間的シーケンスにわたって 出力へ繰り込まれる隠れ状態を計算する。
dictionary MLGruCellOptions : MLOperatorOptions {
  MLOperand bias;
  MLOperand recurrentBias;
  boolean resetAfter = true;
  MLGruWeightLayout layout = "zrn";
  sequence<MLRecurrentNetworkActivation> activations;
};

partial interface MLGraphBuilder {
  MLOperand gruCell(MLOperand input,
                    MLOperand weight,
                    MLOperand recurrentWeight,
                    MLOperand hiddenState,
                    [EnforceRange] unsigned long hiddenSize,
                    optional MLGruCellOptions options = {});
};

dictionary MLGruCellSupportLimits {
  MLTensorLimits input;
  MLTensorLimits weight;
  MLTensorLimits recurrentWeight;
  MLTensorLimits hiddenState;
  MLTensorLimits bias;
  MLTensorLimits recurrentBias;
  MLTensorLimits output;
};

partial dictionary MLOpSupportLimits {
  MLGruCellSupportLimits gruCell;
};

MLGruCellOptions は次のメンバーを持つ:

bias, 型はMLOperand

形状[3 * hiddenSize]の1-D入力バイアステンソル。テンソル形状の第2次元におけるバイアスベクトルの 順序は、layoutに従って指定される。

recurrentBias, 型は MLOperand

形状[3 * hiddenSize]の1-D再帰バイアステンソル。テンソル形状の第2次元におけるバイアスベクトルの 順序は、layoutに従って指定される。

resetAfter, 型はboolean、デフォルトはtrue

行列乗算の後または前にreset gateを適用するかを示す。

layout, 型はMLGruWeightLayout、デフォルトは "zrn"

GRUの内部gate、具体的にはupdate (z)reset (r)、およびnew (n) gateに対するweightおよびbiasベクトルの順序。weightおよびbiasテンソル形状の第2次元で示される。

activations, 型は sequence<MLRecurrentNetworkActivation>

活性化関数のペアを指定する。第1の関数はupdateおよびreset gateに 使用され、第2の関数はnew gateに使用される。指定されない場合、それぞれ"sigmoid" および"tanh" 関数がデフォルトとなる。

引数:

戻り値: MLOperand。 形状[batchSize, hiddenSize]の2-Dテンソルであり、recurrent networkの単一time stepの cell出力隠れ状態。

gruCell()のテンソル制限
オペランド 許可される データ型 許可されるランク
input "float32", "float16" 2
weight input同じ 2
recurrentWeight input同じ 2
bias input同じ 1
recurrentBias input同じ 1
output input同じ 2

MLGruCellSupportLimits は次のメンバーを持つ;

input, 型はMLTensorLimits

inputオペランド用のMLTensorLimits

weight, 型はMLTensorLimits

weightオペランド用のMLTensorLimits

recurrentWeight, 型は MLTensorLimits

recurrentWeightオペランド用のMLTensorLimits

hiddenState, 型はMLTensorLimits

hiddenStateオペランド用のMLTensorLimits

bias, 型はMLTensorLimits

biasオペランド用のMLTensorLimits

recurrentBias, 型はMLTensorLimits

recurrentBiasオペランド用のMLTensorLimits

output, 型はMLTensorLimits

outputオペランド用のMLTensorLimits

MLOpSupportLimitsgruCell()について次のメンバーを持つ:

gruCell, 型はMLGruCellSupportLimits

gruCell()演算子のサポート制限。

gruCell(input, weight, recurrentWeight, hiddenState, hiddenSize, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputweightrecurrentWeighthiddenStateoptions.bias (それが存在する場合)、およびoptions.recurrentBias (それが存在する場合)のいずれかとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. inputweightrecurrentWeight、またはhiddenStateの いずれかのdataTypeが(この表に従う)その許可される データ型のいずれでもない場合、TypeErrorthrowする。

  4. inputweightrecurrentWeightまたはhiddenStateの いずれかのrankが (この表に従う)その許可される ランクでない場合、TypeErrorthrowする。

  5. batchSizeinputshape[0]とする。

  6. inputSizeinputshape[1]とする。

  7. weightshapeが« 3 * hiddenSize, inputSize »と 等しくない場合、TypeErrorthrowする。

  8. recurrentWeightshapeが« 3 * hiddenSize, hiddenSize »と 等しくない場合、TypeErrorthrowする。

  9. hiddenStateshapeが« batchSize, hiddenSize »と 等しくない場合、TypeErrorthrowする。

  10. hiddenSize * 6が有効な次元でない場合、TypeErrorthrowする。

    なぜhiddenSize * 6なのか? 一部の基盤となるプラットフォームは、biasrecurrentBiasを 連結した単一のバイアステンソルを操作する。そのため、3 * hiddenSize + 3 * hiddenSize有効な 次元である必要がある。
  11. options.bias存在する場合:

    1. そのdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

    2. そのshapeが« 3 * hiddenSize »と等しくない場合、TypeErrorthrowする。

  12. options.recurrentBias存在する場合:

    1. そのdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

    2. そのshapeが« 3 * hiddenSize »と等しくない場合、TypeErrorthrowする。

  13. options.activations存在する場合:

    1. そのsizeが2でない場合、TypeErrorthrowする。

    2. activationsを、options.activationsclone とする。

  14. そうでない場合:

    1. activationsを« "sigmoid", "tanh" »とする。

  15. descを、inputdataTypeおよび« batchSize, hiddenSize »が与えられてMLOperandDescriptorを作成する結果とする。

  16. グラフ接続を作成する:

    1. outputを、thisおよび descが与えられてMLOperandを作成する結果とする。

    2. operatorを、weightrecurrentWeighthiddenStatehiddenSizeおよびoptionsが与えられた"gruCell"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputsinputweightrecurrentWeight、およびhiddenStateに設定する。

    5. options.bias存在する場合、それをoperatorinputsに追加する。

    6. options.recurrentBias存在する場合、それをoperatorinputsに追加する。

    7. operator活性化関数を、activationscloneに設定する。

    8. operatoroutputoutputに設定する。

  17. outputを返す。

weight layoutがデフォルトの"zrn" layoutであり、update/reset gateおよびnew gateの活性化関数がそれぞれsigmoid() およびtanh() である場合のこの演算の振る舞いは、ユーザーエージェントは通常より効率的な実装を持つものの、次のように他の演算の 使用から一般的にエミュレートできる。基盤となるプラットフォームが演算を直接サポートしない場合、この分解は 実装を導くためのテンプレートとして使用できる。
function gruCell(
  builder, input, weight, recurrentWeight, hiddenState, hiddenSize, options) {
  const one = builder.constant(input.dataType, 1);
  const zero = builder.constant(input.dataType, 0);

  const inputSize = input.shape[1];

  // update gate (z)
  let z = builder.sigmoid(builder.add(
    builder.add(
      (options.bias ? builder.slice(options.bias, [0], [hiddenSize]) : zero),
      (options.recurrentBias ?
         builder.slice(options.recurrentBias, [0], [hiddenSize]) :
         zero)),
    builder.add(
      builder.matmul(
        input,
        builder.transpose(
          builder.slice(weight, [0, 0], [hiddenSize, inputSize]))),
      builder.matmul(
        hiddenState,
        builder.transpose(
          builder.slice(recurrentWeight, [0, 0], [hiddenSize, hiddenSize]))))));

  // reset gate (r)
  let r = builder.sigmoid(builder.add(
    builder.add(
      (options.bias ? builder.slice(options.bias, [hiddenSize], [hiddenSize]) :
                      zero),
      (options.recurrentBias ?
         builder.slice(options.recurrentBias, [hiddenSize], [hiddenSize]) :
         zero)),
    builder.add(
      builder.matmul(
        input,
        builder.transpose(
          builder.slice(weight, [hiddenSize, 0], [hiddenSize, inputSize]))),
      builder.matmul(
        hiddenState,
        builder.transpose(builder.slice(
          recurrentWeight, [hiddenSize, 0], [hiddenSize, hiddenSize]))))));

  // new gate (n)
  let n;
  if (options.resetAfter) {
    n = builder.tanh(builder.add(
      (options.bias ?
         builder.slice(options.bias, [2 * hiddenSize], [hiddenSize]) :
         zero),
      builder.add(
        builder.matmul(
          input,
          builder.transpose(builder.slice(
            weight, [2 * hiddenSize, 0], [hiddenSize, inputSize]))),
        builder.mul(
          r,
          builder.add(
            (options.recurrentBias ?
               builder.slice(
                 options.recurrentBias, [2 * hiddenSize], [hiddenSize]) :
               zero),
            builder.matmul(
              hiddenState,
              builder.transpose(builder.slice(
                recurrentWeight,
                [2 * hiddenSize, 0],
                [hiddenSize, hiddenSize]))))))));
  } else {
    n = builder.tanh(builder.add(
      builder.add(
        (options.bias ?
           builder.slice(options.bias, [2 * hiddenSize], [hiddenSize]) :
           zero),
        (options.recurrentBias ?
           builder.slice(
             options.recurrentBias, [2 * hiddenSize], [hiddenSize]) :
           zero)),
      builder.add(
        builder.matmul(
          input,
          builder.transpose(builder.slice(
            weight, [2 * hiddenSize, 0], [hiddenSize, inputSize]))),
        builder.matmul(
          builder.mul(r, hiddenState),
          builder.transpose(builder.slice(
            recurrentWeight,
            [2 * hiddenSize, 0],
            [hiddenSize, hiddenSize]))))));
  }

  // compute the new hidden state
  return builder.add(
    builder.mul(z, hiddenState), builder.mul(n, builder.sub(one, z)));
}

8.9.27. hardSigmoid

入力テンソルに対して非平滑なhard sigmoid関数を計算する。 これは、より高速な計算のためにsigmoid関数の代わりに使用される。
dictionary MLHardSigmoidOptions : MLOperatorOptions {
  double alpha = 0.2;
  double beta = 0.5;
};

partial interface MLGraphBuilder {
  MLOperand hardSigmoid(MLOperand input, optional MLHardSigmoidOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits hardSigmoid;
};

MLHardSigmoidOptions は次のメンバーを持つ:

alpha, 型はdouble、デフォルトは0.2

スカラー乗数。

beta, 型はdouble、デフォルトは0.5

スカラー加算値。

引数:

戻り値:

hardSigmoid()のテンソル制限
オペランド 許可される データ型 許可されるランク
input "float32", "float16" N
output input同じ input同じ

MLOpSupportLimitshardSigmoid()について次のメンバーを持つ:

hardSigmoid, 型はMLSingleInputSupportLimits

hardSigmoid()演算子のサポート制限。

hardSigmoid(input, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. inputdataTypeが(この表に従う)その許可されるデータ型 のいずれでもない場合、TypeErrorthrowする。

  4. options.alpha を、options.alphainputdataTypeキャストする結果に設定する。

  5. options.beta を、options.betainputdataTypeキャストする結果に設定する。

  6. グラフ接続を作成する:

    1. outputを、inputが与えられてMLOperandをコピーする結果とする。

    2. operatorを、optionsが与えられた"hardSigmoid"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. operatoroutputoutputに設定する。

  7. outputを返す。

この演算の振る舞いは、ユーザーエージェントは通常より効率的な実装を持つものの、次のように他の演算の 使用から一般的にエミュレートできる。基盤となるプラットフォームが演算を直接サポートしない場合、 この分解は実装を導くためのテンプレートとして使用できる。
function hardSigmoid(builder, input, options) {
  return builder.max(
    builder.min(
      builder.add(
        builder.mul(builder.constant(input.dataType, options.alpha), input),
        builder.constant(input.dataType, options.beta)),
      builder.constant(input.dataType, 1)),
    builder.constant(input.dataType, 0));
}

8.9.28. hardSwish

入力テンソルに対して要素ごとに、[MobileNetV3]で 導入された非線形関数y = x * max(0, min(6, (x + 3))) / 6を計算する。
partial interface MLGraphBuilder {
  MLOperand hardSwish(MLOperand input, optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits hardSwish;
};
引数:

戻り値:

hardSwish()のテンソル制限
オペランド 許可される データ型 許可されるランク
input "float32", "float16" N
output input同じ input同じ

MLOpSupportLimitshardSwish()について次のメンバーを持つ:

hardSwish, 型はMLSingleInputSupportLimits

hardSwish()演算子のサポート制限。

hardSwish(input, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. inputdataTypeが(この表に従う)その許可されるデータ型 のいずれでもない場合、TypeErrorthrowする。

  4. グラフ接続を作成する:

    1. outputを、inputが与えられてMLOperandをコピーする結果とする。

    2. operatorを、optionsが与えられた"hardSwish"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. operatoroutputoutputに設定する。

  5. outputを返す。

この演算の振る舞いは、ユーザーエージェントは通常より効率的な実装を持つものの、次のように他の演算の 使用から一般的にエミュレートできる。基盤となるプラットフォームが演算を直接サポートしない場合、 この分解は実装を導くためのテンプレートとして使用できる。
function hardSwish(builder, input, options) {
  return builder.div(
    builder.mul(
      input,
      builder.max(
        builder.constant(input.dataType, 0),
        builder.min(
          builder.constant(input.dataType, 6),
          builder.add(input, builder.constant(input.dataType, 3))))),
    builder.constant(input.dataType, 6));
}

8.9.29. instanceNormalization

[Instance-Normalization]を使用して 入力を正規化する。batchNormalization()では、 正規化に使用される平均値および分散値はモデルの学習中にbatch次元内のすべてのサンプルにわたって計算されるが、 instance normalizationで使用される平均値および分散値は、batch内の各個別サンプルの各入力特徴量に対して その場で計算される。
dictionary MLInstanceNormalizationOptions : MLOperatorOptions {
  MLOperand scale;
  MLOperand bias;
  double epsilon = 1e-5;
  MLInputOperandLayout layout = "nchw";
};

partial interface MLGraphBuilder {
  MLOperand instanceNormalization(
    MLOperand input,
    optional MLInstanceNormalizationOptions options = {});
};

dictionary MLNormalizationSupportLimits {
  MLTensorLimits input;
  MLTensorLimits scale;
  MLTensorLimits bias;
  MLTensorLimits output;
};

partial dictionary MLOpSupportLimits {
  MLNormalizationSupportLimits instanceNormalization;
};

MLInstanceNormalizationOptions は次のメンバーを持つ:

scale, 型はMLOperand

スケーリング値の1-Dテンソル。そのsizeは channel数、すなわち入力のfeature次元のサイズに等しい。たとえば、input テンソルのlayoutが"nchw" である場合、sizeinputshape[1]に等しい。

bias, 型はMLOperand

バイアス値の1-Dテンソル。そのsizeは 入力のfeature次元のサイズに等しい。たとえば、input テンソルのlayoutが"nchw" である場合、sizeinputshape[1]に等しい。

epsilon, 型はdouble、デフォルトは1e-5

ゼロ除算による計算エラーを防ぐための小さい値。

layout, 型はMLInputOperandLayout、デフォルトは "nchw"

入力のlayout形式。

引数:

戻り値: MLOperandinputと同じ形状の、instance-normalizedされた4-Dテンソル。

instanceNormalization()のテンソル制限
オペランド 許可される データ型 許可されるランク
input "float32", "float16" 4
scale input同じ 1
bias input同じ 1
output input同じ 4

MLNormalizationSupportLimits は次のメンバーを持つ:

input, 型はMLTensorLimits

inputオペランド用のMLTensorLimits

scale, 型はMLTensorLimits

scaleオペランド用のMLTensorLimits

bias, 型はMLTensorLimits

biasオペランド用のMLTensorLimits

output, 型はMLTensorLimits

outputオペランド用のMLTensorLimits

MLOpSupportLimitsinstanceNormalization()について次のメンバーを持つ:

instanceNormalization, 型は MLNormalizationSupportLimits

instanceNormalization()演算子のサポート制限。

instanceNormalization(input, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputoptions.scale (それが存在する場合)、およびoptions.bias (それが存在する場合)のいずれかとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. inputdataTypeが(この表に従う)その許可されるデータ型 のいずれでもない場合、TypeErrorthrowする。

  4. inputrankがその許可されるランクでない場合、TypeErrorthrowする。

  5. options.epsilon を、options.epsiloninputdataTypeキャストする結果に設定する。

  6. axisを、options.layout"nchw" の場合は1、そうでない場合は3とする。

  7. options.scale存在する場合:

    1. そのdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

    2. そのshapeが« inputshape[axis] »と等しくない場合、TypeErrorthrowする。

  8. options.bias存在する場合:

    1. そのdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

    2. そのshapeが« inputshape[axis] »と等しくない場合、TypeErrorthrowする。

  9. グラフ接続を作成する:

    1. outputを、inputが与えられてMLOperandをコピーする結果とする。

    2. operatorを、optionsが与えられた"instanceNormalization"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. options.scale存在する場合、それをoperatorinputsに追加する。

    6. options.bias存在する場合、それをoperatorinputsに追加する。

    7. operatoroutputoutputに設定する。

  10. outputを返す。

入力テンソルが"nchw" layoutの4-Dである場合のこの演算の振る舞いは、ユーザーエージェントは通常より効率的な実装を持つものの、 次のように他の演算の使用から一般的にエミュレートできる。基盤となるプラットフォームが演算を直接サポートしない場合、 この分解は実装を導くためのテンプレートとして使用できる。
function instanceNormalization(builder, input, options) {
  // The reduction of the mean and variance values happens over the spatial
  // dimensions of the input e.g. axis 2 and 3 of the input tensor.
  const reduceOptions = {axes: [2, 3], keepDimensions: true};
  const mean = builder.reduceMean(input, reduceOptions);
  const variance = builder.reduceMean(
    builder.pow(builder.sub(input, mean), builder.constant(input.dataType, 2)),
    reduceOptions);

  // The scale and bias values are applied per input feature
  // e.g. axis 1 of the input tensor.
  const shape = [1, input.shape[1], 1, 1];
  return builder.add(
    builder.mul(
      builder.reshape(options.scale, shape),
      builder.div(
        builder.sub(input, mean),
        builder.sqrt(builder.add(variance, options.epsilon)))),
    builder.reshape(options.bias, shape));
}

8.9.30. layerNormalization

[Layer-Normalization]を使用して入力を正規化する。batchNormalization()では、 平均値および分散値は、モデルの学習中にbatch次元内のすべてのサンプルにわたって計算され、instanceNormalization()では、 平均値および分散値はbatch内の各個別サンプルの各入力特徴量に対してその場で計算されるのに対し、 layer normalizationの平均値および分散値は、batch内の各個別サンプルのすべての入力特徴量にわたって その場で計算される。
dictionary MLLayerNormalizationOptions : MLOperatorOptions {
  MLOperand scale;
  MLOperand bias;
  sequence<[EnforceRange] unsigned long> axes;
  double epsilon = 1e-5;
};

partial interface MLGraphBuilder {
  MLOperand layerNormalization(MLOperand input,
                               optional MLLayerNormalizationOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLNormalizationSupportLimits layerNormalization;
};

MLLayerNormalizationOptions は次のメンバーを持つ:

scale, 型はMLOperand

スケーリング値のN-Dテンソル。そのshapeはaxes メンバーによって決定され、axes 内の各値は、スケーリング値を持つ入力テンソルの次元を示す。たとえば、axes の値が[1,2,3]の場合、このテンソルのshapeは、入力次元1、2および3の対応するサイズのリストである。 このメンバーが存在しない場合、スケーリング値は1とみなされる。

bias, 型はMLOperand

バイアス値のN-Dテンソル。そのshapeはaxes メンバーによって決定され、axes 内の各値は、バイアス値を持つ入力テンソルの次元を示す。たとえば、axes の値が[1,2,3]の場合、このテンソルのshapeは、入力次元1、2および3の対応するサイズのリストである。 このメンバーが存在しない場合、バイアス値は0とみなされる。

axes, 型はsequence<[EnforceRange] unsigned long>

reduceする入力次元へのインデックス。このメンバーが存在しない場合、最初を除くすべての次元が与えられたものとして 扱われる(例: 4-D入力テンソルでは、axes = [1,2,3])。すなわち、平均値および分散値のreductionは、各独立したbatchについて すべての入力特徴量にわたって計算される。空の場合、どの次元もreduceされない。

epsilon, 型はdouble、デフォルトは1e-5

ゼロ除算による計算エラーを防ぐための小さい値。

引数:

戻り値: MLOperandinputと同じ形状の、layer-normalizedされたN-Dテンソル。

layerNormalization()のテンソル制限
オペランド 許可される データ型 許可されるランク
input "float32", "float16" N
scale input同じ N
bias input同じ N
output input同じ input同じ

MLOpSupportLimitslayerNormalization()について次のメンバーを持つ:

layerNormalization, 型はMLNormalizationSupportLimits

layerNormalization()演算子のサポート制限。

layerNormalization(input, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputoptions.scale (それが存在する場合)、およびoptions.bias (それが存在する場合)のいずれかとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. inputdataTypeが(この表に従う)その許可されるデータ型 のいずれでもない場合、TypeErrorthrowする。

  4. options.axes存在しない場合、options.axes を新しいリストに設定する。これは、inputrankが 1より大きい場合は、1からinputrankまでの範囲(排他的)、 そうでない場合は空のリストである。

  5. そうでなく、options.axes が重複する値を含む場合、またはその項目のいずれかが 0からinputrankまでの範囲(排他的)内にない場合、TypeErrorthrowする。

  6. options.epsilon を、options.epsiloninputdataTypeキャストする結果に設定する。

  7. options.scale存在する場合:

    1. そのdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

    2. そのrankoptions.axessizeと等しくない場合、TypeErrorthrowする。

  8. options.bias存在する場合:

    1. そのdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

    2. そのrankoptions.axessizeと等しくない場合、TypeErrorthrowする。

  9. 0からoptions.axessizeまでの範囲(排他的)内の 各indexについて:

    1. axisoptions.axes[index]とする。

    2. axisinputrank以上である場合、TypeErrorthrowする。

    3. sizeinputshape[axis]とする。

    4. options.scale存在する場合:

      1. そのshape[index]が sizeと等しくない場合、TypeErrorthrowする。

    5. options.bias存在する場合:

      1. そのshape[index]が sizeと等しくない場合、TypeErrorthrowする。

  10. グラフ接続を作成する:

    1. outputを、inputが与えられてMLOperandをコピーする結果とする。

    2. operatorを、optionsが与えられた"layerNormalization"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. options.scale存在する場合、それをoperatorinputsに追加する。

    6. options.bias存在する場合、それをoperatorinputsに追加する。

    7. operatoroutputoutputに設定する。

  11. outputを返す。

axesパラメーターが[1,2,3]に設定されている場合のこの演算の振る舞いは、ユーザーエージェントは通常より 効率的な実装を持つものの、次のように他の演算の使用から一般的にエミュレートできる。基盤となる プラットフォームが演算を直接サポートしない場合、この分解は実装を導くためのテンプレートとして使用できる。
function layerNormalization(builder, input, options) {
  // The reduction of the mean and variance values happens over the spatial
  // dimensions across all the input features (i.e. all channels) of the input
  // tensor.
  const reduceOptions = {axes: [1, 2, 3], keepDimensions: true};
  const mean = builder.reduceMean(input, reduceOptions);
  const variance = builder.reduceMean(
    builder.pow(builder.sub(input, mean), builder.constant(input.dataType, 2)),
    reduceOptions);

  // The scale and bias tensors are of the shape of the input
  // specified by the values in the axes parameter (i.e. [1,2,3]).
  return builder.add(
    builder.mul(
      options.scale,
      builder.div(
        builder.sub(input, mean),
        builder.sqrt(builder.add(variance, options.epsilon)))),
    options.bias);
}

8.9.31. leakyRelu

入力テンソルに対して要素ごとに rectified linear functionの leaky版を計算する。計算は式 max(0, x) + alpha * min(0, x)に従う。
dictionary MLLeakyReluOptions : MLOperatorOptions {
  double alpha = 0.01;
};

partial interface MLGraphBuilder {
  MLOperand leakyRelu(MLOperand input, optional MLLeakyReluOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits leakyRelu;
};

MLLeakyReluOptions は次のメンバーを持つ:

alpha, 型はdouble、デフォルトは0.01

スカラー乗数。

引数:

戻り値:

leakyRelu()のテンソル制限
オペランド 許可される データ型 許可されるランク
input "float32", "float16" N
output input同じ input同じ

MLOpSupportLimitsleakyRelu()について次のメンバーを持つ:

leakyRelu, 型はMLSingleInputSupportLimits

leakyRelu()演算子のサポート制限。

leakyRelu(input, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. inputdataTypeが(この表に従う)その許可されるデータ型 のいずれでもない場合、TypeErrorthrowする。

  4. options.alpha を、options.alphainputdataTypeキャストする結果に設定する。

  5. グラフ接続を作成する:

    1. outputを、inputが与えられてMLOperandをコピーする結果とする。

    2. operatorを、optionsが与えられた"leakyRelu"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. operatoroutputoutputに設定する。

  6. outputを返す。

この演算の振る舞いは、ユーザーエージェントは通常より効率的な実装を持つものの、次のように他の演算の 使用から一般的にエミュレートできる。基盤となるプラットフォームが演算を直接サポートしない場合、 この分解は実装を導くためのテンプレートとして使用できる。
function leakyRelu(builder, input, options) {
  return builder.add(
    builder.max(builder.constant(input.dataType, 0), input),
    builder.mul(
      builder.constant(input.dataType, options.alpha),
      builder.min(builder.constant(input.dataType, 0), input)));
}

8.9.32. linear

入力テンソルに対して線形関数y = alpha * x + betaを計算する。
dictionary MLLinearOptions : MLOperatorOptions {
  double alpha = 1;
  double beta = 0;
};

partial interface MLGraphBuilder {
  MLOperand linear(MLOperand input, optional MLLinearOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits linear;
};

MLLinearOptions は次のメンバーを持つ:

alpha, 型はdouble、デフォルトは1

スカラー乗数。

beta, 型はdouble、デフォルトは0

スカラー加算値。

引数:

戻り値:

linear()のテンソル制限
オペランド 許可される データ型 許可されるランク
input "float32", "float16" N
output input同じ input同じ

MLOpSupportLimitslinear()について次のメンバーを持つ:

linear, 型はMLSingleInputSupportLimits

linear()演算子のサポート制限。

linear(input, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. inputdataTypeが(この表に従う)その許可されるデータ型 のいずれでもない場合、TypeErrorthrowする。

  4. options.alpha を、options.alphainputdataTypeキャストする結果に設定する。

  5. options.beta を、options.betainputdataTypeキャストする結果に設定する。

  6. グラフ接続を作成する:

    1. outputを、inputが与えられてMLOperandをコピーする結果とする。

    2. operatorを、optionsが与えられた"linear"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. operatoroutputoutputに設定する。

  7. outputを返す。

この演算の振る舞いは、ユーザーエージェントは通常より効率的な実装を持つものの、次のように他の演算の 使用から一般的にエミュレートできる。基盤となるプラットフォームが演算を直接サポートしない場合、 この分解は実装を導くためのテンプレートとして使用できる。
function linear(builder, input, options) {
  return builder.add(
    builder.mul(input, builder.constant(input.dataType, options.alpha)),
    builder.constant(input.dataType, options.beta));
}

8.9.33. lstm

Long Short-Term Memory [LSTM] recurrent networkは、input、output、forget、およびcell gateを使用して、networkの時間的シーケンスにわたって 出力へ繰り込まれる出力状態を計算する。
enum MLLstmWeightLayout {
  "iofg", // input-output-forget-cell gate ordering
  "ifgo"  // input-forget-cell-output gate ordering
};

dictionary MLLstmOptions : MLOperatorOptions {
  MLOperand bias;
  MLOperand recurrentBias;
  MLOperand peepholeWeight;
  MLOperand initialHiddenState;
  MLOperand initialCellState;
  boolean returnSequence = false;
  MLRecurrentNetworkDirection direction = "forward";
  MLLstmWeightLayout layout = "iofg";
  sequence<MLRecurrentNetworkActivation> activations;
};

partial interface MLGraphBuilder {
  sequence<MLOperand> lstm(MLOperand input,
                           MLOperand weight,
                           MLOperand recurrentWeight,
                           [EnforceRange] unsigned long steps,
                           [EnforceRange] unsigned long hiddenSize,
                           optional MLLstmOptions options = {});
};

dictionary MLLstmSupportLimits {
  MLTensorLimits input;
  MLTensorLimits weight;
  MLTensorLimits recurrentWeight;
  MLTensorLimits bias;
  MLTensorLimits recurrentBias;
  MLTensorLimits peepholeWeight;
  MLTensorLimits initialHiddenState;
  MLTensorLimits initialCellState;
  MLTensorLimits output0;
  MLTensorLimits output1;
  MLTensorLimits output2;
};

partial dictionary MLOpSupportLimits {
  MLLstmSupportLimits lstm;
};

MLLstmOptions は次のメンバーを持つ:

bias, 型はMLOperand

形状[numDirections, 4 * hiddenSize]の2-D入力バイアステンソル。テンソル形状の第2次元におけるバイアス ベクトルの順序は、layoutに従って指定される。

recurrentBias, 型はMLOperand

形状[numDirections, 4 * hiddenSize]の2-D再帰バイアステンソル。テンソル形状の第1次元における バイアスベクトルの順序は、layoutに従って指定される。

peepholeWeight, 型は MLOperand

形状[numDirections, 3 * hiddenSize]のpeephole用2-D weightテンソル。weightベクトルの パック順序は、それぞれinput (i)output (o)、および forget (f) gate用である。

initialHiddenState, 型はMLOperand

形状[numDirections, batchSize, hiddenSize]の3-D初期隠れ状態テンソル。指定されない場合、 実装はゼロで満たされたテンソルを使用しなければならない。

initialCellState, 型は MLOperand

形状[numDirections, batchSize, hiddenSize]の3-D初期隠れ状態テンソル。指定されない場合、 実装はゼロで満たされたテンソルを使用しなければならない。

returnSequence, 型は boolean、デフォルトはfalse

最後のtime stepの出力に加えて、各time stepからのすべての出力を含むシーケンス全体も返すかを示す。

direction, 型はMLRecurrentNetworkDirection、デフォルトは "forward"

入力シーケンスの処理方向。"both"に設定される場合、 weightおよびbiasテンソル形状の第1次元のサイズは2でなければならず、入力は両方向に処理される。

layout, 型はMLLstmWeightLayout、デフォルトは "iofg"

LSTMの内部gate、具体的にはinput (i)output (o)forget (f)、 およびcell (g) gateに対するweightおよびbiasベクトルの順序。weightおよびbiasテンソル形状の 第1次元で示される。

activations, 型は sequence<MLRecurrentNetworkActivation>

3つの活性化関数のリスト。1つ目はinput (i)forget (f)、およびoutput (o) gateに使用され、2つ目は cell (g) gateに使用され、最後は出力cell stateを出力gateの結果と結合して出力隠れ状態を 形成する前にフィルタリングするために使用される。指定されない場合、それぞれ"sigmoid""tanh"、 および"tanh" 関数のシーケンスがデフォルトとなる。

引数:

戻り値: sequence<MLOperand>。 第1要素は形状[numDirections, batchSize, hiddenSize]の3-Dテンソルであり、networkの最後のtime stepからの 出力隠れ状態である。第2要素は形状[numDirections, batchSize, hiddenSize]の3-Dテンソルであり、 networkの最後のtime stepからの出力cell stateである。さらに、returnSequence がtrueに設定されている場合、第3要素は形状[steps, numDirections, batchSize, hiddenSize]の4-D出力テンソルであり、時間的シーケンス内の各time stepからのすべての出力を含む。

lstm()のテンソル制限
オペランド 許可される データ型 許可されるランク
input "float32", "float16" 3
weight input同じ 3
recurrentWeight input同じ 3
bias input同じ 2
recurrentBias input同じ 2
peepholeWeight input同じ 2
initialHiddenState input同じ 3
initialCellState input同じ 3
outputs[0] input同じ 3
outputs[1] input同じ 3
returnSequence がtrueである場合のoutputs[2] input同じ 4

MLLstmSupportLimits は次のメンバーを持つ:

input, 型はMLTensorLimits

inputオペランド用のMLTensorLimits

weight, 型はMLTensorLimits

weightオペランド用のMLTensorLimits

recurrentWeight, 型はMLTensorLimits

recurrentWeightオペランド用のMLTensorLimits

bias, 型はMLTensorLimits

biasオペランド用のMLTensorLimits

recurrentBias, 型は MLTensorLimits

recurrentBiasオペランド用のMLTensorLimits

peepholeWeight, 型は MLTensorLimits

peepholeWeightオペランド用のMLTensorLimits

initialHiddenState, 型はMLTensorLimits

initialHiddenStateオペランド用のMLTensorLimits

initialCellState, 型はMLTensorLimits

initialCellStateオペランド用のMLTensorLimits

output0, 型はMLTensorLimits

すべての出力オペランド[0]用のMLTensorLimits

output1, 型はMLTensorLimits

すべての出力オペランド[1]用のMLTensorLimits

output2, 型はMLTensorLimits

すべての出力オペランド[2]用のMLTensorLimits

MLOpSupportLimitslstm()について次のメンバーを持つ:

lstm, 型はMLLstmSupportLimits

lstm()演算子のサポート制限。

lstm(input, weight, recurrentWeight, steps, hiddenSize, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputweightrecurrentWeightoptions.bias (それが存在する場合)、options.recurrentBias (それが存在する場合)、options.peepholeWeight (それが存在する場合)、options.initialHiddenState (それが存在する場合)、およびoptions.initialCellState (それが存在する場合)のいずれかとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. options.direction"both" である場合はnumDirectionsを2とし、そうでない場合は1とする。

  4. inputweightまたはrecurrentWeightのいずれかのdataTypeが(この表に従う)その許可されるデータ型 のいずれでもない場合、TypeErrorthrowする。

  5. inputweightまたはrecurrentWeightのいずれかのrankが その許可されるランク でない場合、TypeErrorthrowする。

  6. stepsが0である場合、TypeErrorthrowする。

  7. inputshape[0]がstepsと等しくない場合、TypeErrorthrowする。

  8. batchSizeinputshape[1]とする。

  9. inputSizeinputshape[2]とする。

  10. weightshapeが« numDirections, 4 * hiddenSize, inputSize »と等しくない場合、TypeErrorthrowする。

  11. recurrentWeightshapeが« numDirections, 4 * hiddenSize, hiddenSize »と等しくない場合、TypeErrorthrowする。

  12. hiddenSize * 8が有効な次元でない場合、TypeErrorthrowする。

    なぜhiddenSize * 8なのか? 一部の基盤となるプラットフォームは、biasrecurrentBiasを 連結した単一のバイアステンソルを操作する。そのため、4 * hiddenSize + 4 * hiddenSize有効な 次元である必要がある。
  13. options.bias存在する場合:

    1. そのdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

    2. そのshapeが« numDirections, 4 * hiddenSize »と等しくない場合、TypeErrorthrowする。

  14. options.recurrentBias存在する場合:

    1. そのdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

    2. そのshapeが« numDirections, 4 * hiddenSize »と等しくない場合、TypeErrorthrowする。

  15. options.peepholeWeight存在する場合:

    1. そのdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

    2. そのshapeが« numDirections, 3 * hiddenSize »と等しくない場合、TypeErrorthrowする。

  16. options.initialHiddenState存在する場合:

    1. そのdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

    2. そのshapeが« numDirections, batchSize, hiddenSize »と等しくない場合、TypeErrorthrowする。

  17. options.initialCellState存在する場合:

    1. そのdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

    2. そのshapeが« numDirections, batchSize, hiddenSize »と等しくない場合、TypeErrorthrowする。

  18. options.activations存在する場合:

    1. そのsizeが3でない場合、TypeErrorthrowする。

    2. activationsを、options.activationsclone とする。

  19. そうでない場合:

    1. activationsを« "sigmoid", "tanh", "tanh" »とする。

  20. 出力形状を計算する:

    1. descを、inputdataTypeおよび« numDirections, batchSize, hiddenSize »が与えられてMLOperandDescriptorを作成する結果とする。

    2. options.returnSequence がtrueである場合:

      1. desc2を、inputdataType および« steps, numDirections, batchSize, hiddenSize »が与えられてMLOperandDescriptorを作成する結果とする。

  21. グラフ接続を作成する:

    1. operatorを、weightrecurrentWeightstepshiddenSizeおよびoptionsが与えられた"lstm"演算用の演算子とする。

    2. output0を、thisおよび descが与えられてMLOperandを作成する結果とする。

    3. output1を、thisおよび descが与えられてMLOperandを作成する結果とする。

    4. options.returnSequence がtrueである場合:

      1. output2を、this およびdesc2が与えられてMLOperandを作成する結果とする。

      2. outputリスト« output0, output1, output2 »とする。

      3. output0.[[operator]]output1.[[operator]] およびoutput2.[[operator]]operatorに設定する。

    5. そうでない場合:

      1. outputリスト« output0, output1 »とする。

      2. output0.[[operator]] およびoutput1.[[operator]]operatorに設定する。

    6. operatorinputsinputweight、および recurrentWeightに設定する。

    7. options.bias存在する場合、それをoperatorinputsに追加する。

    8. options.recurrentBias存在する場合、それをoperatorinputsに追加する。

    9. options.peepholeWeight存在する場合、それをoperatorinputsに追加する。

    10. options.initialHiddenState存在する場合、それをoperatorinputsに追加する。

    11. options.initialCellState存在する場合、それをoperatorinputsに追加する。

    12. operator活性化関数を、activationscloneに設定する。

    13. operatoroutputoutputに設定する。

  22. outputを返す。

squeeze()ヘルパーを使用すると、この演算の振る舞いは、ユーザーエージェントは 通常より効率的な実装を持つものの、次のように他の演算の使用から一般的にエミュレートできる。 基盤となるプラットフォームが演算を直接サポートしない場合、この分解は実装を導くためのテンプレートとして使用できる。
function lstm(
  builder, input, weight, recurrentWeight, steps, hiddenSize, options) {
  const batchSize = input.shape[1];
  const inputSize = input.shape[2];
  const direction = options.direction || 'forward';
  const numDirections = (direction == 'both' ? 2 : 1);
  let hiddenState = options.initialHiddenState;
  let cellState = options.initialCellState;

  if (!hiddenState) {
    const desc = {
      dataType: 'float32',
      shape: [numDirections, batchSize, hiddenSize]
    };
    const totalSize = numDirections * batchSize * hiddenSize;
    hiddenState = builder.constant(desc, new Float32Array(totalSize).fill(0));
  }

  if (!cellState) {
    const desc = {
      dataType: 'float32',
      shape: [numDirections, batchSize, hiddenSize]
    };
    const totalSize = numDirections * batchSize * hiddenSize;
    cellState = builder.constant(desc, new Float32Array(totalSize).fill(0));
  }

  let currentWeight = [];
  let currentRecurrentWeight = [];
  let currentBias = [];
  let currentRecurrentBias = [];
  let currentPeepholeWeight = [];
  let forwardSequence = null;
  let backwardSequence = null;
  let outputHidden = null;
  let outputCell = null;

  for (let dir = 0; dir < numDirections; ++dir) {
    currentWeight.push(squeeze(
      builder,
      builder.slice(weight, [dir, 0, 0], [1, 4 * hiddenSize, inputSize])));
    currentRecurrentWeight.push(squeeze(
      builder,
      builder.slice(
        recurrentWeight, [dir, 0, 0], [1, 4 * hiddenSize, hiddenSize])));
    currentBias.push(
      options.bias ?
        (squeeze(
          builder,
          builder.slice(options.bias, [dir, 0], [1, 4 * hiddenSize]))) :
        null);
    currentRecurrentBias.push(
      options.recurrentBias ?
        (squeeze(
          builder,
          builder.slice(
            options.recurrentBias, [dir, 0], [1, 4 * hiddenSize]))) :
        null);
    currentPeepholeWeight.push(
      options.peepholeWeight ?
        (squeeze(
          builder,
          builder.slice(
            options.peepholeWeight, [dir, 0], [1, 3 * hiddenSize]))) :
        null);

    let currentHidden = squeeze(
      builder,
      builder.slice(hiddenState, [dir, 0, 0], [1, batchSize, hiddenSize]), [0]);
    let currentCell = squeeze(
      builder,
      builder.slice(cellState, [dir, 0, 0], [1, batchSize, hiddenSize]), [0]);

    for (let step = 0; step < steps; ++step) {
      const slice =
        (dir == 1 || direction == 'backward' ? steps - step - 1 : step);
      const currentInput = squeeze(
        builder,
        builder.slice(input, [slice, 0, 0], [1, batchSize, inputSize]), [0]);

      [currentHidden, currentCell] = builder.lstmCell(
        currentInput,
        currentWeight[dir],
        currentRecurrentWeight[dir],
        currentHidden,
        currentCell,
        hiddenSize,
        {
          bias: currentBias[dir],
          recurrentBias: currentRecurrentBias[dir],
          peepholeWeight: currentPeepholeWeight[dir],
          layout: options.layout,
          activations: options.activations
        });

      if (options.returnSequence) {
        // Expand currentHidden of 2D([batchSize, hiddenSize])
        // to 4D([steps, numDirections, batchSize, hiddenSize])
        const expandedHiddenAs4D =
          builder.reshape(currentHidden, [1, 1, batchSize, hiddenSize]);

        if (direction == 'forward' || (dir == 0 && direction == 'both')) {
          forwardSequence = forwardSequence ?
            builder.concat([forwardSequence, expandedHiddenAs4D], 0) :
            expandedHiddenAs4D;
        } else if (
          direction == 'backward' || (dir == 1 && direction == 'both')) {
          backwardSequence = backwardSequence ?
            builder.concat([expandedHiddenAs4D, backwardSequence], 0) :
            expandedHiddenAs4D;
        }
      }
    }

    // Expand currentHidden of 2D([batchSize, hiddenSize])
    // to 3D([numDirections, batchSize, hiddenSize])
    const expandedHiddenAs3D =
      builder.reshape(currentHidden, [1, batchSize, hiddenSize]);
    outputHidden = outputHidden ?
      builder.concat([outputHidden, expandedHiddenAs3D], 0) :
      expandedHiddenAs3D;

    // Expand currentCell of 2D([batchSize, hiddenSize])
    // to 3D([numDirections, batchSize, hiddenSize])
    const expandedCellAs3D =
      builder.reshape(currentCell, [1, batchSize, hiddenSize]);
    outputCell = outputCell ?
      builder.concat([outputCell, expandedCellAs3D], 0) :
      expandedCellAs3D;
  }

  if (options.returnSequence) {
    let outputSequence = null;

    if (direction == 'forward') {
      outputSequence = forwardSequence;
    } else if (direction == 'backward') {
      outputSequence = backwardSequence;
    } else if (direction == 'both') {
      // Concat along axis 1 (numDirections dimension)
      outputSequence = builder.concat([forwardSequence, backwardSequence], 1);
    }

    return [outputHidden, outputCell, outputSequence];
  } else {
    return [outputHidden, outputCell];
  }
}

8.9.34. lstmCell

Long Short-Term Memory [LSTM] recurrent networkの単一time step。cell state、input、output、およびforget gateを使用して、networkの時間的シーケンスにわたって出力へ繰り込まれる次のtime stepのcell stateとhidden stateを 計算する。
dictionary MLLstmCellOptions : MLOperatorOptions {
  MLOperand bias;
  MLOperand recurrentBias;
  MLOperand peepholeWeight;
  MLLstmWeightLayout layout = "iofg";
  sequence<MLRecurrentNetworkActivation> activations;
};

partial interface MLGraphBuilder {
  sequence<MLOperand> lstmCell(MLOperand input,
                               MLOperand weight,
                               MLOperand recurrentWeight,
                               MLOperand hiddenState,
                               MLOperand cellState,
                               [EnforceRange] unsigned long hiddenSize,
                               optional MLLstmCellOptions options = {});
};

dictionary MLLstmCellSupportLimits {
  MLTensorLimits input;
  MLTensorLimits weight;
  MLTensorLimits recurrentWeight;
  MLTensorLimits hiddenState;
  MLTensorLimits cellState;
  MLTensorLimits bias;
  MLTensorLimits recurrentBias;
  MLTensorLimits peepholeWeight;
  MLTensorLimits output0;
  MLTensorLimits output1;
};

partial dictionary MLOpSupportLimits {
  MLLstmCellSupportLimits lstmCell;
};

MLLstmCellOptions は次のメンバーを持つ:

bias, 型はMLOperand

形状[4 * hiddenSize]の1-D入力バイアステンソル。テンソル形状の第1次元におけるバイアスベクトルの順序は、 layoutに従って指定される。

recurrentBias, 型は MLOperand

形状[4 * hiddenSize]の1-D再帰バイアステンソル。テンソル形状の第1次元におけるバイアスベクトルの順序は、 layoutに従って指定される。

peepholeWeight, 型は MLOperand

形状[3 * hiddenSize]のpeephole用1-D weightテンソル。weightベクトルのパック順序は、 それぞれinput (i)output (o)、および forget (f) gate用である。

layout, 型はMLLstmWeightLayout、デフォルトは "iofg"

LSTMの内部gate、具体的にはinput (i)output (o)forget (f)、 およびcell (g) gateに対するweightおよびbiasベクトルの順序。weightおよびbiasテンソル形状の 第1次元で示される。

activations, 型は sequence<MLRecurrentNetworkActivation>

3つの活性化関数のリスト。1つ目はinput (i)forget (f)、およびoutput (o) gateに使用され、2つ目は cell (g) gateに使用され、最後は出力cell stateを出力gateの結果と結合して出力hidden stateを 形成する前にフィルタリングするために使用される。指定されない場合、それぞれ"sigmoid""tanh"、 および"tanh" 関数のシーケンスがデフォルトとなる。

引数:

戻り値: sequence<MLOperand>。 第1要素はrecurrent networkの現在のtime stepの出力hidden stateである。 次の要素は出力cell stateである。両方の要素は形状[batchSize, hiddenSize]の2-Dテンソルである。

lstmCell()のテンソル制限
オペランド 許可される データ型 許可されるランク
input "float32", "float16" 2
weight input同じ 2
recurrentWeight input同じ 2
hiddenState input同じ 2
cellState input同じ 2
bias input同じ 1
recurrentBias input同じ 1
peepholeWeight input同じ 1
outputs[0] input同じ 2
outputs[1] input同じ 2

MLLstmCellSupportLimits は次のメンバーを持つ:

input, 型はMLTensorLimits

inputオペランド用のMLTensorLimits

weight, 型はMLTensorLimits

weightオペランド用のMLTensorLimits

recurrentWeight, 型は MLTensorLimits

recurrentWeightオペランド用のMLTensorLimits

hiddenState, 型はMLTensorLimits

hiddenStateオペランド用のMLTensorLimits

cellState, 型はMLTensorLimits

cellStateオペランド用のMLTensorLimits

bias, 型はMLTensorLimits

biasオペランド用のMLTensorLimits

recurrentBias, 型はMLTensorLimits

recurrentBiasオペランド用のMLTensorLimits

peepholeWeight, 型はMLTensorLimits

peepholeWeightオペランド用のMLTensorLimits

output0, 型はMLTensorLimits

すべての出力オペランド[0]用のMLTensorLimits

output1, 型はMLTensorLimits

すべての出力オペランド[1]用のMLTensorLimits

MLOpSupportLimitslstmCell()について次のメンバーを持つ:

lstmCell, 型はMLLstmCellSupportLimits

lstmCell()演算子のサポート制限。

lstmCell(input, weight, recurrentWeight, hiddenState, cellState, hiddenSize, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputweightrecurrentWeighthiddenStatecellStateoptions.bias (それが存在する場合)、options.recurrentBias (それが存在する場合)、およびoptions.peepholeWeight (それが存在する場合)のいずれかとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. inputweightrecurrentWeighthiddenStateまたはcellStateのいずれかのdataTypeが (この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

  4. inputweightrecurrentWeighthiddenState またはcellStateのいずれかのrankが その許可されるランクでない場合、TypeErrorthrowする。

  5. batchSizeinputshape[0]とする。

  6. inputSizeinputshape[1]とする。

  7. weightshapeが« 4 * hiddenSize, inputSize »と等しくない場合、TypeErrorthrowする。

  8. recurrentWeightshapeが« 4 * hiddenSize, hiddenSize »と等しくない場合、TypeErrorthrowする。

  9. hiddenStateshapeが« batchSize, hiddenSize »と等しくない場合、 TypeErrorthrowする。

  10. cellStateshapeが« batchSize, hiddenSize »と等しくない場合、 TypeErrorthrowする。

  11. hiddenSize * 8が妥当な次元でない場合、TypeErrorthrowする。

    なぜhiddenSize * 8なのか? 一部の基盤となるプラットフォームは、biasrecurrentBiasを 連結した単一のバイアステンソルを操作する。そのため、4 * hiddenSize + 4 * hiddenSize妥当な 次元である必要がある。
  12. options.bias存在する場合:

    1. そのdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

    2. そのshapeが« 4 * hiddenSize »と等しくない場合、TypeErrorthrowする。

  13. options.recurrentBias存在する場合:

    1. そのdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

    2. そのshapeが« 4 * hiddenSize »と等しくない場合、TypeErrorthrowする。

  14. options.peepholeWeight存在する場合:

    1. そのdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

    2. そのshapeが« 3 * hiddenSize »と等しくない場合、TypeErrorthrowする。

  15. options.activations存在する場合:

    1. そのsizeが3でない場合、TypeErrorthrowする。

    2. activationsを、options.activationsclone とする。

  16. そうでない場合:

    1. activationsを« "sigmoid", "tanh", "tanh" »とする。

  17. descを新しいMLOperandDescriptorとする。

  18. desc.shapeリスト« batchSize, hiddenSize »に設定する。

  19. desc.dataTypeinputdataTypeに設定する。

  20. グラフ接続を作成する:

    1. output0を、thisおよび descが与えられてMLOperandを作成する結果とする。

    2. output1を、thisおよび descが与えられてMLOperandを作成する結果とする。

    3. outputリスト« output0, output1 »とする。

    4. operatorを、weightrecurrentWeighthiddenStatecellStatehiddenSizeおよびoptionsが与えられた"lstmCell"演算用の演算子とする。

    5. output0.[[operator]] およびoutput1.[[operator]]operatorに設定する。

    6. operatorinputsinputweightrecurrentWeighthiddenState、およびcellStateに設定する。

    7. options.bias存在する場合、それをoperatorinputsに追加する。

    8. options.recurrentBias存在する場合、それをoperatorinputsに追加する。

    9. options.peepholeWeight存在する場合、それをoperatorinputsに追加する。

    10. operator活性化関数を、activationscloneに設定する。

    11. operatoroutputoutputに設定する。

  21. outputを返す。

weight layoutがデフォルトの"iofg" layoutであり、input/forget/output gateの活性化関数および cell gate/output hidden state用のcell stateフィルターがそれぞれsigmoid() およびtanh() である場合のこの演算の振る舞いは、ユーザーエージェントは通常より効率的な実装を持つものの、次のように他の 演算の使用から一般的にエミュレートできる。基盤となるプラットフォームが演算を直接サポートしない場合、 この分解は実装を導くためのテンプレートとして使用できる。
function lstmCell(
  builder,
  input,
  weight,
  recurrentWeight,
  hiddenState,
  cellState,
  hiddenSize,
  options) {
  const zero = builder.constant(input.dataType, 0);

  const inputSize = input.shape[1];

  // input gate (i)
  let i = builder.sigmoid(builder.add(
    builder.mul(
      cellState,
      (options.peepholeWeight ?
         builder.slice(options.peepholeWeight, [0], [hiddenSize]) :
         zero)),
    builder.add(
      builder.add(
        (options.bias ? builder.slice(options.bias, [0], [hiddenSize]) : zero),
        (options.recurrentBias ?
           builder.slice(options.recurrentBias, [0], [hiddenSize]) :
           zero)),
      builder.add(
        builder.matmul(
          input,
          builder.transpose(
            builder.slice(weight, [0, 0], [hiddenSize, inputSize]))),
        builder.matmul(
          hiddenState,
          builder.transpose(builder.slice(
            recurrentWeight, [0, 0], [hiddenSize, hiddenSize])))))));

  // forget gate (f)
  let f = builder.sigmoid(builder.add(
    builder.mul(
      cellState,
      (options.peepholeWeight ?
         builder.slice(options.peepholeWeight, [2 * hiddenSize], [hiddenSize]) :
         zero)),
    builder.add(
      builder.add(
        (options.bias ?
           builder.slice(options.bias, [2 * hiddenSize], [hiddenSize]) :
           zero),
        (options.recurrentBias ?
           builder.slice(
             options.recurrentBias, [2 * hiddenSize], [hiddenSize]) :
           zero)),
      builder.add(
        builder.matmul(
          input,
          builder.transpose(builder.slice(
            weight, [2 * hiddenSize, 0], [hiddenSize, inputSize]))),
        builder.matmul(
          hiddenState,
          builder.transpose(builder.slice(
            recurrentWeight,
            [2 * hiddenSize, 0],
            [hiddenSize, hiddenSize])))))));

  // cell gate (g)
  let g = builder.tanh(builder.add(
    builder.add(
      (options.bias ?
         builder.slice(options.bias, [3 * hiddenSize], [hiddenSize]) :
         zero),
      (options.recurrentBias ?
         builder.slice(options.recurrentBias, [3 * hiddenSize], [hiddenSize]) :
         zero)),
    builder.add(
      builder.matmul(
        input,
        builder.transpose(
          builder.slice(weight, [3 * hiddenSize, 0], [hiddenSize, inputSize]))),
      builder.matmul(
        hiddenState,
        builder.transpose(builder.slice(
          recurrentWeight, [3 * hiddenSize, 0], [hiddenSize, hiddenSize]))))));

  // output gate (o)
  let o = builder.sigmoid(builder.add(
    builder.mul(
      cellState,
      (options.peepholeWeight ?
         builder.slice(options.peepholeWeight, [hiddenSize], [hiddenSize]) :
         zero)),
    builder.add(
      builder.add(
        (options.bias ?
           builder.slice(options.bias, [hiddenSize], [hiddenSize]) :
           zero),
        (options.recurrentBias ?
           builder.slice(options.recurrentBias, [hiddenSize], [hiddenSize]) :
           zero)),
      builder.add(
        builder.matmul(
          input,
          builder.transpose(
            builder.slice(weight, [hiddenSize, 0], [hiddenSize, inputSize]))),
        builder.matmul(
          hiddenState,
          builder.transpose(builder.slice(
            recurrentWeight, [hiddenSize, 0], [hiddenSize, hiddenSize])))))));

  // output cell state (ct)
  let ct = builder.add(builder.mul(f, cellState), builder.mul(i, g));

  // output hidden state (ht)
  let ht = builder.mul(o, builder.tanh(ct));

  return [ht, ct];
}

8.9.35. matmul

2つの入力テンソルの行列積を計算する。
partial interface MLGraphBuilder {
  MLOperand matmul(MLOperand a, MLOperand b, optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLBinarySupportLimits matmul;
};
引数:

戻り値: MLOperand。 2つの入力テンソルの行列積を含む出力テンソル。

2つの入力テンソルの行列積を次のように計算する:
matmul()のテンソル制限
オペランド 許可される データ型 許可されるランク
a "float32", "float16" 2 から N
b a同じ 2 または N
output a同じ 2 または N

MLOpSupportLimitsmatmul()について次のメンバーを持つ:

matmul, 型はMLBinarySupportLimits

matmul()演算子のサポート制限。

matmul(a, b, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびabのいずれかとともに行った結果がfalseを返す場合、 TypeErrorthrowする。

  3. aまたはbのいずれかのdataTypeが (この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

  4. 出力形状を計算する:

    1. shapeAを、ashapeclone とする。

    2. rankAarankとする。

    3. shapeBを、bshapeclone とする。

    4. rankBbrankとする。

    5. rankAまたはrankBのいずれかが2未満である場合、TypeErrorthrowする。

    6. colsAshapeA[rankA - 1]とする。

    7. rowsAshapeA[rankA - 2]とする。

    8. colsBshapeB[rankB - 1]とする。

    9. rowsBshapeB[rankB - 2]とする。

    10. colsArowsBと等しくない場合、TypeErrorthrowする。

    11. batchShapeAを、spatial dimensions(最後の2項目)が削除されたshapeAclone とする。

    12. batchShapeBを、spatial dimensions(最後の2項目)が削除されたshapeBclone とする。

    13. outputShapeを、batchShapeAbatchShapeB双方向ブロードキャストする結果とする。 それが失敗を返す場合、TypeErrorthrowする。

    14. « rowsA, colsB »をoutputShape付加する

    15. descを、adataTypeおよびoutputShapeが与えられてMLOperandDescriptorを作成する結果とする。

  5. グラフ接続を作成する:

    1. outputを、thisおよび descが与えられてMLOperandを作成する結果とする。

    2. operatorを、optionsが与えられた"matmul"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputsaおよびbに設定する。

    5. operatoroutputoutputに設定する。

  6. outputを返す。

8.9.36. pad

テンソルの端に定数値またはmirror値を用いてテンソルを拡張する。
enum MLPaddingMode {
  "constant",
  "edge",
  "reflection"
};

dictionary MLPadOptions : MLOperatorOptions {
  MLPaddingMode mode = "constant";
  MLNumber value = 0;
};

partial interface MLGraphBuilder {
  MLOperand pad(MLOperand input,
                sequence<[EnforceRange] unsigned long> beginningPadding,
                sequence<[EnforceRange] unsigned long> endingPadding,
                optional MLPadOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits pad;
};

MLPadOptions は次のメンバーを持つ:

mode, 型はMLPaddingMode、デフォルトは "constant"

テンソルをpadするための異なる方法。

value, 型はMLNumber、デフォルトは0

mode"constant"に設定されている場合のpadding値。

引数:

戻り値: MLOperand。 padされた出力テンソル。出力テンソルの各次元は次のように計算できる:

output size = beginning padding + input size + ending padding

pad()のテンソル制限
オペランド 許可される データ型 許可されるランク
input 任意 N
output input同じ input同じ

MLOpSupportLimitspad()について次のメンバーを持つ:

pad, 型はMLSingleInputSupportLimits

pad()演算子のサポート制限。

pad(input, beginningPadding, endingPadding, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. beginningPaddingsizeendingPaddingsizeの両方が inputrankと等しくない場合、TypeErrorthrowする。

  4. descinput.[[descriptor]]のcopyとする。

  5. outputShapeinputshapeのcopyとする。

  6. 0からoutputShaperankまで(含まない)の範囲内の各indexについて実行する:

    1. options.modeで分岐する:

      "constant"

      何もしない。

      "edge"

      何もしない。

      "reflection"
      1. beginningPadding[index]が outputShape[index]以上である場合、TypeErrorthrowする。

      2. endingPadding[index]が outputShape[index]以上である場合、TypeErrorthrowする。

    2. beginningPadding[index]の値を outputShape[index]に加算する。

    3. endingPadding[index]の値を outputShape[index]に加算する。

  7. outputShape内のいずれかのitem妥当な次元でない場合、TypeErrorthrowする。

  8. options.value を、options.valueinputdataTypecastした結果に設定する。

  9. desc.shapeoutputShapeに設定する。

  10. グラフ接続を作成する:

    1. outputを、thisおよび descが与えられてMLOperandを作成する結果とする。

    2. operatorを、beginningPaddingendingPaddingおよび optionsが与えられた"padding"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. operatoroutputoutputに設定する。

  11. outputを返す。

constant、edge、およびreflection paddingの例:
// input: [[1,2,3], [4,5,6]]
const input = builder.constant(
  {dataType: 'float32', shape: [2, 3]}, new Float32Array([1, 2, 3, 4, 5, 6]));

const beginningPadding = [1, 2];
const endingPadding = [1, 2];

// "constant" padded:
//    [[0,0,0,0,0,0,0],
//     [0,0,1,2,3,0,0],
//     [0,0,4,5,6,0,0],
//     [0,0,0,0,0,0,0]]
builder.pad(input, beginningPadding, endingPadding);

// "edge" padded:
//    [[1,1,1,2,3,3,3],
//     [1,1,1,2,3,3,3],
//     [4,4,4,5,6,6,6],
//     [4,4,4,5,6,6,6]]
builder.pad(input, beginningPadding, endingPadding, {mode: 'edge'});

// "reflection" padded:
//    [[6,5,4,5,6,5,4],
//     [3,2,1,2,3,2,1],
//     [6,5,4,5,6,5,4],
//     [3,2,1,2,3,2,1]]
builder.pad(input, beginningPadding, endingPadding, {mode: 'reflection'});

8.9.37. Pooling operations

入力テンソル上を移動するwindow内のすべての要素にわたってpooling演算を計算する。
enum MLRoundingType {
  "floor",
  "ceil"
};

dictionary MLPool2dOptions : MLOperatorOptions {
  sequence<[EnforceRange] unsigned long> windowDimensions;
  sequence<[EnforceRange] unsigned long> padding;
  sequence<[EnforceRange] unsigned long> strides;
  sequence<[EnforceRange] unsigned long> dilations;
  MLInputOperandLayout layout = "nchw";
  MLRoundingType outputShapeRounding = "floor";
  sequence<[EnforceRange] unsigned long> outputSizes;
};

partial interface MLGraphBuilder {
  MLOperand averagePool2d(MLOperand input, optional MLPool2dOptions options = {});
  MLOperand l2Pool2d(MLOperand input, optional MLPool2dOptions options = {});
  MLOperand maxPool2d(MLOperand input, optional MLPool2dOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits averagePool2d;
  MLSingleInputSupportLimits l2Pool2d;
  MLSingleInputSupportLimits maxPool2d;
};

MLPool2dOptions は次のメンバーを持つ:

windowDimensions, 型は sequence<[EnforceRange] unsigned long>

長さ2のリスト: [windowHeight, windowWidth]。 sliding windowの寸法を指定する。 window寸法のデフォルト値は、入力形状のheightおよびwidth寸法である。

padding, 型はsequence<[EnforceRange] unsigned long>

長さ4のリスト: [beginningHeight, endingHeight, beginningWidth, endingWidth]。 convolution入力の各spatial dimensionの先頭および末尾に追加される行および列を指定する。 デフォルト値は[0,0,0,0]である。

strides, 型はsequence<[EnforceRange] unsigned long>

長さ2のリスト: [strideHeight, strideWidth]。 convolution入力の各spatial dimensionについてsliding windowのstrideを指定する。 デフォルト値は[1,1]である。

dilations, 型はsequence<[EnforceRange] unsigned long>

長さ2のリスト: [dilationHeight, dilationWidth]。convolution filter(kernel)に適用される各 spatial dimensionのdilation係数を指定する。 デフォルト値は[1,1]である。

layout, 型はMLInputOperandLayout、デフォルトは "nchw"

入力および出力テンソルのlayout形式を次のように指定する:

  • "nchw"

    • input tensor: [batches, inputChannels, height, width]

    • output tensor: [batches, outputChannels, height, width]

  • "nhwc":

    • input tensor: [batches, height, width, inputChannels]

    • output tensor: [batches, height, width, outputChannels]

outputShapeRounding, 型はMLRoundingType、デフォルトは "floor"

完全なwindow結果または部分的なwindow結果のどちらが望まれるかに応じて、出力形状を計算するために使用される丸め関数。

outputSizes, 型は sequence<[EnforceRange] unsigned long>

長さ2のリスト: [outputHeight, outputWidth] 出力テンソルの2つのspatial dimensionのサイズを指定する。 出力サイズが明示的に指定されている場合、outputShapeRounding は無視される。 指定されていない場合、出力サイズは自動的に計算される。

引数:

戻り値: MLOperand。 reductionの結果を含む出力4-Dテンソル。論理形状はlayoutの値に従って解釈される。 より具体的には、outputShapeRounding"floor"の場合、 出力テンソルの単一次元についてのspatial dimensionは次のように計算できる:

output size = floor(1 + (input size - filter size + beginning padding + ending padding) / stride)

または、outputShapeRounding"ceil"の場合:

output size = ceil(1 + (input size - filter size + beginning padding + ending padding) / stride)

pooling演算のテンソル制限
オペランド 許可される データ型 許可されるランク
input 演算手順の一部として指定される 4
output input同じ 4

MLOpSupportLimits はpooling演算について次のメンバーを持つ:

averagePool2d, 型は MLSingleInputSupportLimits

averagePool2d()演算子のサポート制限。

l2Pool2d, 型はMLSingleInputSupportLimits

l2Pool2d()演算子のサポート制限。

maxPool2d, 型はMLSingleInputSupportLimits

maxPool2d()演算子のサポート制限。

max pooling演算のようなglobal pooling演算は、window寸法が入力形状のspatial dimensions(最後の2次元)である poolingの変種であり、次のようになる。
// 'global' max pooling
builder.maxPool2d(input);
string opMLOperand inputMLPool2dOptions options、および任意のlist allowedDataTypesが与えられて、pooling演算を作成するには、次の手順を実行する:
  1. Assert: opは"averagePool2d"、"l2Pool2d"、 "maxPool2d"のいずれかである。

  2. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  3. オペランドを検証することをthisおよびinputとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  4. allowedDataTypesが与えられており、それが inputdataType含まない場合、TypeErrorthrowする。

  5. inputrankが4でない場合、TypeErrorthrowする。

  6. options.layoutで分岐する:

    "nchw"

    « batches, channels, inputHeight, inputWidth »をinputshapeとする。

    "nhwc"

    « batches, inputHeight, inputWidth, channels »をinputshapeとする。

  7. options.windowDimensions存在しない場合、options.windowDimensions を« inputHeight, inputWidth »に設定する。

  8. options.windowDimensionssizeが2でない場合、TypeErrorthrowする。

  9. options.windowDimensions 内のいずれかのitemが0に等しい場合、TypeErrorthrowする。

  10. options.outputSizes存在する場合、またはoptions.padding存在しない場合、options.paddingリスト« 0, 0, 0, 0 »に設定する。

  11. options.paddingsizeが4でない場合、TypeErrorthrowする。

  12. options.strides存在しない場合、options.stridesリスト« 1, 1 »に設定する。

  13. options.stridessizeが2でない場合、TypeErrorthrowする。

  14. options.strides 内のいずれかのitemが0である場合、TypeErrorthrowする。

  15. options.outputSizes存在する場合:

    1. そのsizeが2でない場合、TypeErrorthrowする。

    2. そのitemsoptions.stridesの 同じ次元(index)にあるitems より小さくない場合、TypeErrorthrowする。

  16. options.dilations存在しない場合、options.dilationsリスト« 1, 1 »に設定する。

  17. options.dilationssizeが2でない場合、TypeErrorthrowする。

  18. options.dilations 内のいずれかのitemが0である場合、TypeErrorthrowする。

  19. descinput.[[descriptor]]のcopyとする。

  20. 出力形状を計算する:

    1. « windowHeight, windowWidth »をoptions.windowDimensions とする。

    2. « calculatedOutputHeight, calculatedOutputWidth »を、 inputHeightinputWidthwindowHeightwindowWidthoptions.paddingoptions.strides、 およびoptions.dilationsが与えられてconv2d output sizesを計算する結果とする。

    3. options.outputSizes存在する場合:

      1. « outputHeight, outputWidth »を options.outputSizes とする。

      2. outputHeightがfloor( calculatedOutputHeight )に等しく、かつoutputWidthがfloor( calculatedOutputWidth )に等しい、またはoutputHeightがceil( calculatedOutputHeight )に等しく、かつoutputWidthがceil( calculatedOutputWidth )に等しい、のどちらでもない場合、TypeErrorthrowする。

    4. そうでない場合:

      1. « outputHeight, outputWidth »を« calculatedOutputHeight, calculatedOutputWidth »とする。

      2. options.outputShapeRoundingで分岐する:

        "floor"
        1. outputWidthをfloor(outputWidth)に設定する。

        2. outputHeightをfloor(outputHeight)に設定する。

        "ceil"
        1. outputWidthをceiling(outputWidth)に設定する。

        2. outputHeightをceiling(outputHeight)に設定する。

    5. outputHeightまたはoutputWidthのいずれかが妥当な 次元でない場合、TypeErrorthrowする。

    6. options.layoutで分岐する:

      "nchw"

      outputShapeを« batches, channels, outputHeight, outputWidth »とする。

      "nhwc"

      outputShapeを« batches, outputHeight, outputWidth, channels »とする。

    7. desc.shapeoutputShapeに設定する。

  21. グラフ接続を作成する:

    1. outputを、thisおよび descが与えられてMLOperandを作成する結果とする。

    2. operatorを、optionsが与えられたop演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. operatoroutputoutputに設定する。

  22. outputを返す。

次のpoolingアルゴリズムがサポートされる。
averagePool2d(input, options) メソッドの手順は次のとおりである:
  1. outputを、"averagePool2d"、inputoptions、および« "float32", "float16" »が与えられてpooling演算を作成する結果とする。

    1. それがエラーをthrowsする場合、そのエラーを再throwする。

  2. outputを返す。

l2Pool2d(input, options) メソッドの手順は次のとおりである:
  1. outputを、"l2Pool2d"、inputoptions、および« "float32", "float16" »が与えられてpooling演算を作成する結果とする。

    1. それがエラーをthrowsする場合、そのエラーを再throwする。

  2. outputを返す。

maxPool2d(input, options) メソッドの手順は次のとおりである:
  1. outputを、"maxPool2d"、inputおよびoptionsが与えられてpooling演算を作成する結果とする。

    1. それがエラーをthrowsする場合、そのエラーを再throwする。

  2. outputを返す。

8.9.37.1. averagePool2d
feature mapのpatchについて平均値を計算し、それを使用してpooled feature mapを作成する。詳細は§ 8.9.37 Pooling operationsを参照。
8.9.37.2. l2Pool2d
L2 norm関数を入力feature mapの領域に適用する。L2 normは、その要素の二乗和の平方根である。詳細は§ 8.9.37 Pooling operationsを参照。
8.9.37.3. maxPool2d
feature mapのpatchについて最大値を計算し、それを使用してpooled feature mapを作成する。詳細は§ 8.9.37 Pooling operationsを参照。

8.9.38. prelu

入力テンソルに対してrectified linear functionのparametric版(Parametric ReLU)を要素単位で計算する。Parametric ReLUは leaky ReLUの一種であり、0.01のようなスカラーslopeを持つ代わりに、slope(leakage係数)を この演算のmodel training段階で学習されるパラメーターにする。計算は式max(0, x) + slope * min(0, x)に従う。

演算はbroadcastされる。 これは[numpy-broadcasting-rule]に従う。入力テンソルは双方向ブロードキャスト可能でなければならない。出力テンソルのrankは、入力テンソルの最大rankである。 出力テンソルの各次元について、そのサイズは入力テンソルのその次元に沿った最大サイズである。

partial interface MLGraphBuilder {
  MLOperand prelu(MLOperand input,
                  MLOperand slope,
                  optional MLOperatorOptions options = {});
};

dictionary MLPreluSupportLimits {
  MLTensorLimits input;
  MLTensorLimits slope;
  MLTensorLimits output;
};

partial dictionary MLOpSupportLimits {
  MLPreluSupportLimits prelu;
};
引数:

戻り値:

prelu()のテンソル制限
オペランド 許可される データ型 許可されるランク
input "float32", "float16", "int64", "int32", "int8" N
slope input同じ N
output input同じ N

MLPreluSupportLimits は次のメンバーを持つ:

input, 型はMLTensorLimits

inputオペランド用のMLTensorLimits

slope, 型はMLTensorLimits

slopeオペランド用のMLTensorLimits

output, 型はMLTensorLimits

outputオペランド用のMLTensorLimits

MLOpSupportLimitsprelu()について次のメンバーを持つ:

prelu, 型はMLPreluSupportLimits

prelu()演算子のサポート制限。

prelu(input, slope, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputslopeのいずれかとともに行った結果が falseを返す場合、TypeErrorthrowする。

  3. inputまたは slopeのいずれかのdataTypeが(この表に従う)その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

  4. outputShapeを、slopeshapeおよびinputshape双方向ブロードキャストする結果とする。

    1. それが失敗を返す場合、TypeErrorthrowする。

  5. descriptorを、inputdataTypeおよび outputShapeが与えられてMLOperandDescriptorを作成する結果とする。

  6. グラフ接続を作成する:

    1. outputを、thisおよび descriptorが与えられてMLOperandを作成する結果とする。

    2. operatorを、slopeおよびoptionsが与えられた"prelu"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputsinputおよびslopeに設定する。

    5. operatoroutputoutputに設定する。

  7. outputを返す。

この演算の振る舞いは、ユーザーエージェントは通常より効率的な実装を持つものの、次のように他の演算の使用から 一般的にエミュレートできる。基盤となるプラットフォームが演算を直接サポートしない場合、 この分解は実装を導くためのテンプレートとして使用できる。
function prelu(builder, input, slope) {
  return builder.add(
    builder.max(builder.constant(input.dataType, 0), input),
    builder.mul(
      slope, builder.min(builder.constant(input.dataType, 0), input)));
}

8.9.39. Reduction operations

入力テンソルをすべての次元に沿って、またはaxes 配列パラメーターで指定された軸に沿ってreduceする。指定された各軸について、そのindexを持つ次元がreduceされる。すなわち、結果のテンソルは、 keepDimensions が指定されていない限り、それを含まない。結果のテンソルの値は、reduceされた次元にわたるすべての入力値をパラメーターとして取る、 指定されたreduction関数を使用して計算される。
dictionary MLReduceOptions : MLOperatorOptions {
  sequence<[EnforceRange] unsigned long> axes;
  boolean keepDimensions = false;
};

partial interface MLGraphBuilder {
  MLOperand reduceL1(MLOperand input, optional MLReduceOptions options = {});
  MLOperand reduceL2(MLOperand input, optional MLReduceOptions options = {});
  MLOperand reduceLogSum(MLOperand input, optional MLReduceOptions options = {});
  MLOperand reduceLogSumExp(MLOperand input, optional MLReduceOptions options = {});
  MLOperand reduceMax(MLOperand input, optional MLReduceOptions options = {});
  MLOperand reduceMean(MLOperand input, optional MLReduceOptions options = {});
  MLOperand reduceMin(MLOperand input, optional MLReduceOptions options = {});
  MLOperand reduceProduct(MLOperand input, optional MLReduceOptions options = {});
  MLOperand reduceSum(MLOperand input, optional MLReduceOptions options = {});
  MLOperand reduceSumSquare(MLOperand input, optional MLReduceOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits reduceL1;
  MLSingleInputSupportLimits reduceL2;
  MLSingleInputSupportLimits reduceLogSum;
  MLSingleInputSupportLimits reduceLogSumExp;
  MLSingleInputSupportLimits reduceMax;
  MLSingleInputSupportLimits reduceMean;
  MLSingleInputSupportLimits reduceMin;
  MLSingleInputSupportLimits reduceProduct;
  MLSingleInputSupportLimits reduceSum;
  MLSingleInputSupportLimits reduceSumSquare;
};

MLReduceOptions は次のメンバーを持つ:

axes, 型はsequence<[EnforceRange] unsigned long>

reduceする次元。これにより、入力テンソル内のどの値がreduction関数で使用されるかも指定される。リスト内のaxesは、 入力テンソルのrankをNとすると、 [0, N-1]の範囲内でなければならない。

存在しない場合、すべての次元がreduceされる。reduction関数への入力値は、入力テンソル内のすべての値である。

存在し、空でない場合、reduction関数への入力値は、入力テンソルの指定された次元についてのすべての値である。

存在し、空である場合、どの次元もreduceされず、出力テンソルの形状は入力テンソルの形状と同じになる。reduction関数は、 テンソル内の各値に個別に適用される。

keepDimensions, 型は boolean、デフォルトはfalse

trueの場合、出力は入力と同じrankを持ち、reduceされたすべての次元をサイズ1に設定する。

引数:

戻り値: MLOperandinputrankを含む、 0からそのrankまでの範囲にあるrankの出力N-Dテンソルであり、 axes およびkeepDimensions に依存する。入力オペランドがスカラーである場合、reduction関数はそのスカラー値に適用され、出力もスカラーである。

reduction演算のテンソル制限
オペランド 許可される データ型 許可されるランク
input 演算手順の一部として指定される N
output input同じ N

MLOpSupportLimits はreduction演算について次のメンバーを持つ:

reduceL1, 型はMLSingleInputSupportLimits

reduceL1()演算子のサポート制限。

reduceL2, 型はMLSingleInputSupportLimits

reduceL2()演算子のサポート制限。

reduceLogSum, 型は MLSingleInputSupportLimits

reduceLogSum()演算子のサポート制限。

reduceLogSumExp, 型は MLSingleInputSupportLimits

reduceLogSumExp()演算子のサポート制限。

reduceMax, 型はMLSingleInputSupportLimits

reduceMax()演算子のサポート制限。

reduceMean, 型はMLSingleInputSupportLimits

reduceMean()演算子のサポート制限。

reduceMin, 型はMLSingleInputSupportLimits

reduceMin()演算子のサポート制限。

reduceProduct, 型は MLSingleInputSupportLimits

reduceProduct()演算子のサポート制限。

reduceSum, 型はMLSingleInputSupportLimits

reduceSum()演算子のサポート制限。

reduceSumSquare, 型は MLSingleInputSupportLimits

reduceSumSquare()演算子のサポート制限。

Reduction types:
unsigned integersのlist inputShape、任意のunsigned integersのlist axes、およびboolean keepDimensionsが与えられて、reduction output sizesを計算するには、次の手順を実行する。 それらはunsigned integersの新しいlist、 またはfailureを返す。
  1. inputRankinputShapesizeとする。

  2. axesが与えられていない場合、axesを0から inputRankまで(含まない)の範囲とする。

  3. そうでなく、axesが重複値を含む場合、またはそのitemsのいずれかが 0からinputRankまで(含まない)の範囲内にない場合、failureを返す。

  4. keepDimensionsがtrueの場合:

    1. outputShapeinputShapeclone とする。

    2. axesの各axisについて実行する:

      1. outputShape[axis]を1に設定する。

  5. そうでない場合:

    1. outputShapeを空のlistとする。

    2. 0からinputRankまで(含まない)の範囲 内の各indexについて実行する:

      1. axesindex含まない場合、inputShape[index] をoutputShapeappendする。

  6. outputShapeを返す。

string opMLOperand inputMLReduceOptions options、および任意のlist allowedDataTypesが与えられて、reduction operationを作成するには、次の手順を実行する:
  1. Assert: opは"reduceL1"、"reduceL2"、 "reduceLogSum"、"reduceLogSumExp"、"reduceMax"、"reduceMean"、"reduceMin"、"reduceProduct"、 "reduceSum"、"reduceSumSquare"のいずれかである。

  2. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  3. オペランドを検証することをthisおよびinputとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  4. allowedDataTypesが与えられており、それが inputdataType含まない場合、TypeErrorthrowする。

  5. outputShapeを、inputshapeoptions.axes (それが存在する場合)、およびoptions.keepDimensionsが与えられてreduction output sizesを計算する結果とする。 それがfailureを返す場合、TypeErrorthrowする。

  6. descを、inputdataTypeおよび outputShapeが与えられてMLOperandDescriptorを作成する結果とする。

  7. グラフ接続を作成する:

    1. outputを、thisおよび descが与えられてMLOperandを作成する結果とする。

    2. operatorを、optionsが与えられたop演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. operatoroutputoutputに設定する。

  8. outputを返す。

次のreductionアルゴリズムがサポートされる。
reduceL1(input, options) メソッドの手順は次のとおりである:
  1. outputを、"reduceL1"、inputoptions、および« "float32", "float16", "int32", "uint32", "int64", "uint64" »が与えられてreduction operationを作成する結果とする。

    1. それがエラーをthrowsする場合、そのエラーを再throwする。

  2. outputを返す。

reduceL2(input, options) メソッドの手順は次のとおりである:
  1. outputを、"reduceL2"、inputoptions、および« "float32", "float16" »が与えられてreduction operationを作成する結果とする。

    1. それがエラーをthrowsする場合、そのエラーを再throwする。

  2. outputを返す。

reduceLogSum(input, options) メソッドの手順は次のとおりである:
  1. outputを、"reduceLogSum"、inputoptions、および« "float32", "float16" »が与えられてreduction operationを作成する結果とする。

    1. それがエラーをthrowsする場合、そのエラーを再throwする。

  2. outputを返す。

reduceLogSumExp(input, options) メソッドの手順は次のとおりである:
  1. outputを、"reduceLogSumExp"、inputoptions、および« "float32", "float16" »が与えられてreduction operationを作成する結果とする。

    1. それがエラーをthrowsする場合、そのエラーを再throwする。

  2. outputを返す。

reduceMax(input, options) メソッドの手順は次のとおりである:
  1. outputを、"reduceMax"、inputおよびoptionsが与えられてreduction operationを作成する結果とする。

    1. それがエラーをthrowsする場合、そのエラーを再throwする。

  2. outputを返す。

reduceMean(input, options) メソッドの手順は次のとおりである:
  1. outputを、"reduceMean"、inputoptions、および« "float32", "float16" »が与えられてreduction operationを作成する結果とする。

    1. それがエラーをthrowsする場合、そのエラーを再throwする。

  2. outputを返す。

reduceMin(input, options) メソッドの手順は次のとおりである:
  1. outputを、"reduceMin"、inputおよびoptionsが与えられてreduction operationを作成する結果とする。

    1. それがエラーをthrowsする場合、そのエラーを再throwする。

  2. outputを返す。

reduceProduct(input, options) メソッドの手順は次のとおりである:
  1. outputを、"reduceProduct"、inputoptions、および« "float32", "float16", "int32", "uint32", "int64", "uint64" »が与えられてreduction operationを作成する結果とする。

    1. それがエラーをthrowsする場合、そのエラーを再throwする。

  2. outputを返す。

reduceSum(input, options) メソッドの手順は次のとおりである:
  1. outputを、"reduceSum"、inputoptions、および« "float32", "float16", "int32", "uint32", "int64", "uint64" »が与えられてreduction operationを作成する結果とする。

    1. それがエラーをthrowsする場合、そのエラーを再throwする。

  2. outputを返す。

reduceSumSquare(input, options) メソッドの手順は次のとおりである:
  1. outputを、"reduceSumSquare"、inputoptions、および« "float32", "float16", "int32", "uint32", "int64", "uint64" »が与えられてreduction operationを作成する結果とする。

    1. それがエラーをthrowsする場合、そのエラーを再throwする。

  2. outputを返す。

いくつかのreduction演算の振る舞いは、ユーザーエージェントは通常より効率的な実装を持つものの、次のように他の演算の使用から 一般的にエミュレートできる。基盤となるプラットフォームが演算を直接サポートしない場合、 この分解は実装を導くためのテンプレートとして使用できる。
function reduceLogSum(builder, input, options) {
  return builder.log(builder.reduceSum(input, options));
}

function reduceLogSumExp(builder, input, options) {
  return builder.log(builder.reduceSum(builder.exp(input), options));
}

function reduceSumSquare(builder, input, options) {
  return builder.reduceSum(builder.pow(input, 2), options);
}
一部の基盤となるプラットフォームは、keepDimensions のようなoptionを直接サポートしない。これは基盤となるテンソルデータには影響せず、形状にのみ影響する。たとえば、入力形状が [2, 3, 4]、axisが1、かつkeepDimensions がtrueの場合、期待される出力形状は[2, 1 ,4]である。基盤となるプラットフォームがreduceされた 次元を保持しない場合、それは[2, 4]の出力形状を生成する。実装は[2, 1, 4]へのno-op reshapeを導入できる。keepDimensions がfalseであっても、基盤となるプラットフォームが常にreduceされた次元を保持する場合、同様のno-op reshapeを導入できる。

8.9.40. relu

入力テンソルのrectified linear functionを計算する。
partial interface MLGraphBuilder {
  MLOperand relu(MLOperand input, optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits relu;
};
引数:

戻り値:

relu()のテンソル制限
オペランド 許可される データ型 許可されるランク
input "float32", "float16", "int64", "int32", "int8" N
output input同じ input同じ

MLOpSupportLimitsrelu()について次のメンバーを持つ:

relu, 型はMLSingleInputSupportLimits

relu()演算子のサポート制限。

relu(input, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. inputdataTypeが(この表に従う) その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

  4. グラフ接続を作成する:

    1. outputを、inputが与えられてMLOperandをcopyする結果とする。

    2. operatorを、optionsが与えられた"relu"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. operatoroutputoutputに設定する。

  5. outputを返す。

この演算の振る舞いは、ユーザーエージェントは通常より効率的な実装を持つものの、次のように他の演算の使用から 一般的にエミュレートできる。基盤となるプラットフォームが演算を直接サポートしない場合、 この分解は実装を導くためのテンプレートとして使用できる。
function relu(builder, input) {
  return builder.max(builder.constant(input.dataType, 0), input);
}

8.9.41. resample2d

軸およびスケーリング係数に従って、テンソル値をソース次元から宛先次元へresampleする。
enum MLInterpolationMode {
  "nearest-neighbor",
  "linear"
};

dictionary MLResample2dOptions : MLOperatorOptions {
  MLInterpolationMode mode = "nearest-neighbor";
  sequence<float> scales;
  sequence<[EnforceRange] unsigned long> sizes;
  sequence<[EnforceRange] unsigned long> axes;
};

partial interface MLGraphBuilder {
  MLOperand resample2d(MLOperand input, optional MLResample2dOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits resample2d;
};
引数:

戻り値: MLOperand。 出力4-Dテンソル。

MLResample2dOptions は次のメンバーを持つ:

mode, 型はMLInterpolationMode、デフォルトは "nearest-neighbor"

出力テンソル値を埋めるために使用される補間アルゴリズム。

どちらのアルゴリズムも、各spatial axis(axesに基づく)について計算された、 次の入力から開始する。ここで、inputSizeinput テンソルのshapeで与えられ、 outputSizesizes またはscalesで与えられ、 outputCoordinateは、計算対象の出力テンソル内の要素を識別する。

scale = outputSize / inputSize
unclampedCoordinate = (outputCoordinate + 0.5) / scale - 0.5
inputCoordinate = clamp(unclampedCoordinate, 0, inputSize - 1)
出力テンソル内の所与のoutputCoordinate.xおよびoutputCoordinate.yの位置について、 上の式は有理数のinputCoordinate.xおよび inputCoordinate.yを与える。
nearest-neighbor

上で計算されたinputCoordinate.xおよびinputCoordinate.yは、 次のように出力テンソル値を計算するため、nearest-neighbor samplingアルゴリズムへの入力として使用される:

x = ceil(inputCoordinate.x - 0.5)
y = ceil(inputCoordinate.y - 0.5)
output tensor value = input tensor value at (x, y)
linear

上で計算されたinputCoordinate.xおよびinputCoordinate.yは、 次のように出力テンソル値を計算するため、bilinear samplingアルゴリズムへの入力として使用される:

x0 = floor(inputCoordinate.x)
x1 = ceil(inputCoordinate.x)
y0 = floor(inputCoordinate.y)
y1 = ceil(inputCoordinate.y)
vx0y0 = input tensor value at (x0, y0)
vx1y0 = input tensor value at (x1, y0)
vx0y1 = input tensor value at (x0, y1)
vx1y1 = input tensor value at (x1, y1)
tx = inputCoordinate.x - x0
ty = inputCoordinate.y - y0

vy0 = vx0y0 * (1 - tx) + vx1y0 * tx
vy1 = vx0y1 * (1 - tx) + vx1y1 * tx
output tensor value = vy0 * (1 - ty) + vy1 * ty
scales, 型は sequence<float>

長さ2のリスト。 axesからの各入力次元についてのスケーリング係数を指定する: [scaleForFirstAxis, scaleForSecondAxis]。 デフォルト値は[1.0, 1.0]である。

sizes, 型はsequence<[EnforceRange] unsigned long>

長さ2のリスト。 axesからの各入力次元についてのターゲットサイズを指定する: [sizeForFirstAxis, sizeForSecondAxis]sizes が指定されている場合、スケーリング係数値は入力のターゲットサイズから導出されるため、scales は無視される。

axes, 型はsequence<[EnforceRange] unsigned long>

長さ2のリスト。 補間アルゴリズムが適用される入力テンソルの2つの次元を指定する。 デフォルト値は[2, 3]である。

resample2d()のテンソル制限
オペランド 許可される データ型 許可されるランク
input "float32", "float16", "uint8", "int8" 4
output input同じ 4

MLOpSupportLimitsresample2d()について次のメンバーを持つ:

resample2d, 型はMLSingleInputSupportLimits

resample2d()演算子のサポート制限。

resample2d(input, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. inputdataTypeが(この表に従う) その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

  4. inputrankがその許可されるrankでない場合、TypeErrorthrowする。

  5. options.scales存在しない場合、それをlist « 1.0, 1.0 »に設定する。

  6. そうでなく、そのitemsのいずれかが0以下である、またはそのsizeが2でない場合、TypeErrorthrowする。

  7. options.sizes存在する場合で、そのsizeが2でない、 またはそのitemsのいずれかが0である場合、TypeErrorthrowする。

  8. options.axes存在しない場合、それをlist « 2, 3 »に設定する。

  9. そうでなく、options.axes が重複値を含む、またはそのitemsのいずれかが 0からinputrankまで(含まない)の範囲内にない場合、TypeErrorthrowする。

  10. 出力形状を計算する:

    1. inputDescriptorinput.[[descriptor]]とする。

    2. outputShapeinputDescriptor.shapeclone とする。

    3. 0からoptions.axessizeまで(含まない)の範囲 内の各indexについて実行する:

      1. options.sizes存在する場合、sizeoptions.sizes[index]とする。

      2. そうでない場合、sizeをfloor(inputshape[options.axes[index]] * options.scales[index])とする。

      3. size妥当な次元でない場合、TypeErrorthrowする。

      4. outputShape[options.axes[index]] をsizeに設定する。

    4. descを、inputDescriptor.dataType およびoutputShapeが与えられてMLOperandDescriptorを作成する結果とする。

  11. グラフ接続を作成する:

    1. outputを、thisおよび descが与えられてMLOperandを作成する結果とする。

    2. operatorを、optionsが与えられた"resample2d"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. operatoroutputoutputに設定する。

  12. outputを返す。

具体的なsamplingアルゴリズムは、既存のMachine Learningフレームワークで広く使用されているものに基づく。たとえば、 次の[4, 4]入力テンソル(spatial dimensionsのみを考慮)からlinear resamplingを行う場合:
[   0   1   2   3  ]
[   0   1   2   3  ]
[  12  13  14  15  ]
[  12  13  14  15  ]

[8, 8]出力テンソルについて、期待される値は次のとおりである:

[   0   0.25   0.75   1.25   1.75   2.25   2.75   3  ]
[   0   0.25   0.75   1.25   1.75   2.25   2.75   3  ]
[   0   0.25   0.75   1.25   1.75   2.25   2.75   3  ]
[   3   3.25   3.75   4.25   4.75   5.25   5.75   6  ]
[   9   9.25   9.75  10.25  10.75  11.25  11.75  12  ]
[  12  12.25  12.75  13.25  13.75  14.25  14.75  15  ]
[  12  12.25  12.75  13.25  13.75  14.25  14.75  15  ]
[  12  12.25  12.75  13.25  13.75  14.25  14.75  15  ]

これは、samplingが均等に分散され、対称で、image mirroringに対して堅牢で、corner値が揃うという便利な性質を持つ。

8.9.42. reshape

テンソルの形状を新しい形状へ変更する。Reshapeはテンソルの内容をcopyしたり変更したりしない。 後続の演算のためにテンソルの論理形状を変更するだけである。
partial interface MLGraphBuilder {
  MLOperand reshape(MLOperand input,
                    sequence<[EnforceRange] unsigned long> newShape,
                    optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits reshape;
};
引数:

戻り値: MLOperand。 出力テンソル。出力テンソルの値は入力テンソルの値と同じである。出力テンソルの形状はnewShape により指定される。

reshape()のテンソル制限
オペランド 許可される データ型 許可されるランク
input 任意 N
output input同じ N

MLOpSupportLimitsreshape()について次のメンバーを持つ:

reshape, 型はMLSingleInputSupportLimits

reshape()演算子のサポート制限。

reshape(input, newShape, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. newShapesizeが(この表に従う)出力テンソルの許可されるランクでない場合、TypeErrorthrowする。

  4. outputShapeunsigned longの空配列とする。

  5. newShapesizeが0の場合、outputShapeをスカラー用の空のlist に設定する。

  6. newShape内のいずれかのitem妥当な次元でない場合、TypeErrorthrowする。

  7. inputElementCountを、inputshape内のすべてのitemsの積とする。 空の次元はinputElementCountを1にする。

  8. newShape内のすべての値の積がinputElementCountと等しくない場合、TypeErrorthrowする。

  9. descinput.[[descriptor]] のcopyとする。

  10. desc.shapenewShapeに設定する。

  11. グラフ接続を作成する:

    1. outputを、thisおよび descが与えられてMLOperandを作成する結果とする。

    2. operatorを、optionsが与えられた"reshape"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. operatoroutputoutputに設定する。

  12. outputを返す。

8.9.43. reverse

指定された軸に沿ってテンソルをreverseする。
dictionary MLReverseOptions : MLOperatorOptions {
  sequence<[EnforceRange] unsigned long> axes;
};

partial interface MLGraphBuilder {
  MLOperand reverse(MLOperand input, optional MLReverseOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits reverse;
};

MLReverseOptions は次のメンバーを持つ:

axes, 型はsequence<[EnforceRange] unsigned long>

reverseする入力次元へのindex。このメンバーが存在しない場合、すべての次元がreverseされるものとして扱われる。 明示的に空として渡された場合、どの次元もreverseされない。

引数:

戻り値:

reverse()のテンソル制限
オペランド 許可される データ型 許可されるランク
input 任意 N
output input同じ input同じ

MLOpSupportLimitsreverse()について次のメンバーを持つ:

reverse, 型はMLSingleInputSupportLimits

reverse()演算子のサポート制限。

reverse(input, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. inputdataTypeが(この表に従う) その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

  4. inputRankinputrankとする。

  5. axesが与えられていない場合、axesを0から inputRankまで(含まない)の範囲とする。

  6. そうでなく、axesが重複値を含む、またはその要素のいずれかが0から inputRankまで(含まない)の範囲内にない場合、failureを返す。

  7. グラフ接続を作成する:

    1. outputを、inputが与えられてMLOperandをcopyする結果とする。

    2. operatorを、"reverse"演算およびoptions用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. operatoroutputoutputに設定する。

  8. outputを返す。

8.9.44. scatterElements

indicesに従って、axisに沿って、updatesテンソルからの値を入力テンソルのcopyの上にscatterする。
dictionary MLScatterOptions : MLOperatorOptions {
  [EnforceRange] unsigned long axis = 0;
};

partial interface MLGraphBuilder {
  MLOperand scatterElements(MLOperand input,
                            MLOperand indices,
                            MLOperand updates,
                            optional MLScatterOptions options = {});
};

dictionary MLScatterSupportLimits {
  MLTensorLimits input;
  MLTensorLimits indices;
  MLTensorLimits updates;
  MLTensorLimits output;
};

partial dictionary MLOpSupportLimits {
  MLScatterSupportLimits scatterElements;
};

MLScatterOptions は次のメンバーを持つ:

axis, 型はunsigned long、デフォルトは0

scattered valuesが取得される軸。その値は、入力テンソルのrankをNとすると、 [0, N-1]の範囲内でなければならない。

引数:

戻り値: MLOperandinputrankと等しいrankの出力N-Dテンソル。

scatterElements()のテンソル制限
オペランド 許可される データ型 許可されるランク
input 任意 1からNまで
indices "int32", "uint32", "int64" input同じ
updates input同じ input同じ
output input同じ input同じ

MLScatterSupportLimits は次のメンバーを持つ:

input, 型はMLTensorLimits

inputオペランド用のMLTensorLimits

indices, 型はMLTensorLimits

indicesオペランド用のMLTensorLimits

updates, 型はMLTensorLimits

updatesオペランド用のMLTensorLimits

output, 型はMLTensorLimits

outputオペランド用のMLTensorLimits

MLOpSupportLimitsscatterElements()について次のメンバーを持つ:

scatterElements, 型は MLScatterSupportLimits

scatterElements()演算子のサポート制限。

indices パラメーターをscatterElements() に渡す場合、グラフが構築される時点では入力が実行まで分からないため、許可された範囲にclampできない。 指定されたclampingの振る舞いが基盤となるプラットフォームにより提供されない場合、実装はcompile済みグラフにclamp() を導入できる。同様に、基盤となるプラットフォームが負のindicesをサポートしない場合、実装はcompile済みグラフに 負のindexを次元の末尾からのpositive indexへ変換する演算を導入できる。
scatterElements(input, indices, updates, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputindicesupdatesのいずれかとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. indicesdataTypeが(この表に従う) その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

  4. updatesdataTypeinputdataTypeと等しくない場合、TypeErrorthrowする。

  5. inputindices、またはupdatesのいずれかのrankが その許可されるrankでない場合、 TypeErrorthrowする。

  6. axisoptions.axisとする。

  7. axisinputrank以上である場合、TypeErrorthrowする。

  8. indicesShapeExpectedinputshapeのcopyとする。

  9. indicesShapeExpected[axis]をindicesshape[axis]に設定する。

  10. indicesshapeindicesShapeExpected等しくない場合、TypeErrorthrowする。

  11. updatesshapeindicesshape等しくない場合、TypeErrorthrowする。

  12. グラフ接続を作成する:

    1. outputを、inputが与えられてMLOperandをcopyする結果とする。

    2. operatorを、inputindicesupdates、 およびoptionsが与えられた"scatterElements"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputsinputindices、 およびupdatesに設定する。

    5. operatoroutputoutputに設定する。

  13. outputを返す。

scatterElementsが異なるslicing schemesでどのように動作するかの例。
// input of shape [4,3]:
//   [[ 0,  1,  2],
//    [10, 11, 12],
//    [20, 21, 22],
//    [30, 31, 32]]
// indices of shape [2,3]:
//   [[3, 1, 1],
//    [2, 0, 3]]
// updates of shape [2,3]:
//   [[-1, -2, -3],
//    [-4, -5, -6]]
// axis = 0 (default)
// output of shape [4,3]:
//   [[ 0, -5,  2],
//    [10, -2, -3],
//    [-4, 21, 22],
//    [-1, 31, -6]]

const input1 = builder.constant(
  {dataType: 'float32', shape: [4, 3]},
  new Float32Array([0, 1, 2, 10, 11, 12, 20, 21, 22, 30, 31, 32]));

const indices1 = builder.constant(
  {dataType: 'uint32', shape: [2, 3]}, new Uint32Array([3, 1, 1, 2, 0, 3]));

const updates1 = builder.constant(
  {dataType: 'float32', shape: [2, 3]},
  new Uint32Array([-1, -2, -3, -4, -5, -6]));

const output1 = builder.scatterElements(input1, indices1, updates1);

// input of shape [4,3]:
//   [[ 0,  1,  2],
//    [10, 11, 12],
//    [20, 21, 22],
//    [30, 31, 32]]
// indices of shape [4,1]:
//   [[2],
//    [1],
//    [0],
//    [2]],
// updates of shape [4,1]:
//   [[-1],
//    [-2],
//    [-3],
//    [-4]],
// axis = 1
// output of shape [4,3]:
//   [[ 0,  1, -1],
//    [10, -2, 12],
//    [-3, 21, 22],
//    [30, 31, -4]]

const indices2 = builder.constant(
  {dataType: 'uint32', shape: [4, 1]}, new Uint32Array([2, 1, 0, 2]));

const updates2 = builder.constant(
  {dataType: 'float32', shape: [4, 1]}, new Uint32Array([-1, -2, -3, -4]));

const output2 = builder.scatterElements(input1, indices2, updates2, {axis: 1});

// input of shape [4,2,2]:
//   [[[  0,   1],
//     [ 10,  11]],
//    [[100, 101],
//     [110, 111]],
//    [[200, 201],
//     [210, 211]],
//    [[300, 301],
//     [310, 311]],]
// indices of shape [1,2,2]:
//   [[[0, 2],
//     [1, 3]]],
// updates of shape [1,2,2]:
//   [[[-1, -2],
//     [-3, -4]]],
// axis = 0
// output of shape [4,2,2]:
//   [[[ -1,   1],
//     [ 10,  11]],
//    [[100, 101],
//     [ -3, 111]],
//    [[200,  -2],
//     [210, 211]],
//    [[300, 301],
//     [310,  -4]],]

const inputData3 = new Float32Array(
  [0, 1, 10, 11, 100, 101, 110, 111, 200, 201, 210, 211, 300, 301, 310, 311]);

const input3 =
  builder.constant({dataType: 'float32', shape: [4, 2, 2]}, inputData3);

const indices3 = builder.constant(
  {dataType: 'uint32', shape: [1, 2, 2]}, new Uint32Array([0, 2, 1, 3]));

const updates3 = builder.constant(
  {dataType: 'float32', shape: [1, 2, 2]}, new Uint32Array([-1, -2, -3, -4]));

const output3 = builder.scatterElements(input3, indices3, updates3, {axis: 0});

8.9.45. scatterND

indicesに従って、updateテンソルからの値のslicesを入力テンソルのcopyの上にscatterする。
partial interface MLGraphBuilder {
  MLOperand scatterND(MLOperand input,
                      MLOperand indices,
                      MLOperand updates,
                      optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLScatterSupportLimits scatterND;
};
引数:

戻り値: MLOperandinputrank + indicesrank - indicesshape[-1] - 1に等しいrankの出力N-Dテンソル。

scatterND()のテンソル制限
オペランド 許可される データ型 許可されるランク
input 任意 1からNまで
indices "int32", "uint32", "int64" 1からNまで
updates input同じ N
output input同じ 1からNまで

MLOpSupportLimitsscatterND()について次のメンバーを持つ:

scatterND, 型はMLScatterSupportLimits

scatterND()演算子のサポート制限。

indices パラメーターをscatterND() に渡す場合、グラフが構築される時点では入力が実行まで分からないため、許可された範囲にclampできない。 指定されたclampingの振る舞いが基盤となるプラットフォームにより提供されない場合、実装はcompile済みグラフにclamp() を導入できる。同様に、基盤となるプラットフォームが負のindicesをサポートしない場合、実装はcompile済みグラフに 負のindexを次元の末尾からのpositive indexへ変換する演算を導入できる。
scatterND(input, indices, updates, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputindicesupdatesのいずれかとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. indicesdataTypeが(この表に従う)許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

  4. updatesdataTypeinputdataTypeと等しくない場合、TypeErrorthrowする。

  5. inputindices、またはupdatesのいずれかのrankが その許可されるrankでない場合、 TypeErrorthrowする。

  6. inputShapeinputshapeとし、inputRankinputrankとする。

  7. indicesShapeindicesshapeとし、indicesRankindicesrankとする。

  8. indexableSizeindicesRank - 1とする。

  9. coordinateSizeindicesShape[indexableSize]とする。

  10. coordinateSizeinputRankより大きい場合、TypeErrorthrowする。

  11. expectedUpdatesShapeを空listとする。

  12. 0からindexableSizeまで(含まない)の範囲内の各indexについて実行する:

    1. indicesShape[index]を expectedUpdatesShapeappendする。

  13. coordinateSizeからinputRankまで(含まない)の範囲 内の各indexについて実行する:

    1. inputShape[index]を expectedUpdatesShapeappendする。

  14. updatesshapeexpectedUpdatesShape等しくない場合、TypeErrorthrowする。

  15. outputShapeinputshapeのcopyとする。

  16. outputDescを、inputdataTypeおよび outputShapeが与えられてMLOperandDescriptorを作成する結果とする。

  17. グラフ接続を作成する:

    1. outputを、outputDescが与えられてMLOperandを作成する結果とする。

    2. operatorを、inputindicesupdates、 およびoptionsが与えられた"scatterND"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputsinputindices、 およびupdatesに設定する。

    5. operatoroutputoutputに設定する。

  18. outputを返す。

scatterNDが異なるslicing schemesでどのように動作するかの例。
// input of shape [8]:
//   [0, 1, 2, 3, 4, 5, 6, 7]
// indices of shape [4, 1]:
//   [[4],
//    [3],
//    [1],
//    [7]]
// updates of shape [4]:
//   [-1, -2, -3, -4]
// output of shape [8]:
//   [0, -3, 2, -2, -1, 5, 6, -4]

const input1 = builder.constant(
  {dataType: 'float32', shape: [8]},
  new Float32Array([0, 1, 2, 3, 4, 5, 6, 7]));

const indices1 = builder.constant(
  {dataType: 'uint32', shape: [4, 1]}, new Uint32Array([4, 3, 1, 7]));

const updates1 = builder.constant(
  {dataType: 'uint32', shape: [4]}, new Uint32Array([-1, -2, -3, -4]));

const output1 = builder.scatterND(input1, indices1, updates1);

// input of shape [2,2]:
//   [[0, 1],
//    [2, 3]]
// indices of shape [2,2]:
//   [[0, 0],
//    [1, 1]]
// updates of shape [2]:
//   [-1, -2]
// output of shape [2,2]:
//   [[-1,  1],   <= -1 written to output coordinate [0, 0]
//    [ 2, -2]]   <= -2 written to output coordinate [1, 1]

const input2 = builder.constant(
  {dataType: 'float32', shape: [2, 2]}, new Float32Array([0, 1, 2, 3]));

const indices2 = builder.constant(
  {dataType: 'uint32', shape: [2, 2]}, new Uint32Array([0, 0, 1, 1]));

const updates2 =
  builder.constant({dataType: 'uint32', shape: [2]}, new Uint32Array([-1, -2]));

const output2 = builder.scatterND(input2, indices2, updates2);

// input of shape [3,2]:
//   [[0, 1],
//    [2, 3],
//    [4, 5]]
// indices of shape [2,1]:
//   [[2],
//    [0]]
// updates of shape [2,2]:
//   [[-1, -2],
//    [-3, -4]]
// output of shape [3,2]:
//   [[-3 ,-4],    <= [-3, -4] written to output coordinates [0, *]
//    [ 2,  3],
//    [-1, -2]]    <= [-1, -2] written to output coordinates [2, *]

const input3 = builder.constant(
  {dataType: 'float32', shape: [3, 2]}, new Float32Array([0, 1, 2, 3, 4, 5]));

const indices3 = builder.constant(
  {dataType: 'uint32', shape: [2, 1]}, new Uint32Array([1, 0]));

const updates3 = builder.constant(
  {dataType: 'uint32', shape: [2, 2]}, new Uint32Array([-1, -2, -3, 4]));

const output3 = builder.scatterND(input3, indices3, updates3);

// input of shape [2,2,2]:
//   [[[0, 1],
//     [2, 3]],
//    [[4, 5],
//     [6, 7]]]
// indices of shape [2,2]:
//   [[0, 1],
//    [1, 0]]
// updates of shape [2,2]:
//   [[-1, -2],
//    [-3, -4]]
// output of shape [2,2,2]:
//   [[[ 0,  1],
//     [-1, -2]],   <= [-1, -2] written to output coordinates [0, 1, *]
//    [[-3, -4],    <= [-3, -4] written to output coordinates [1, 0, *]
//     [ 6,  7]]]

const input4 = builder.constant(
  {dataType: 'float32', shape: [2, 2, 2]},
  new Float32Array([0, 1, 2, 3, 4, 5, 6, 7]));

const indices4 = builder.constant(
  {dataType: 'uint32', shape: [2, 2]}, new Uint32Array([0, 1, 1, 0]));

const updates4 = builder.constant(
  {dataType: 'uint32', shape: [2, 2]}, new Uint32Array([-1, -2, -3, 4]));

const output4 = builder.scatterND(input4, indices4, updates4);

8.9.46. sigmoid

入力テンソルのsigmoid functionを計算する。 計算は式1 / (exp(-x) + 1)に従う。
partial interface MLGraphBuilder {
  MLOperand sigmoid(MLOperand input, optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits sigmoid;
};
引数:

戻り値:

sigmoid()のテンソル制限
オペランド 許可される データ型 許可されるランク
input "float32", "float16" N
output input同じ input同じ

MLOpSupportLimitssigmoid()について次のメンバーを持つ:

sigmoid, 型はMLSingleInputSupportLimits

sigmoid()演算子のサポート制限。

sigmoid(input, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. inputdataTypeが(この表に従う) その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

  4. グラフ接続を作成する:

    1. outputを、inputが与えられてMLOperandをcopyする結果とする。

    2. operatorを、optionsが与えられた"sigmoid"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. operatoroutputoutputに設定する。

  5. outputを返す。

この演算の振る舞いは、ユーザーエージェントは通常より効率的な実装を持つものの、次のように他の演算の使用から 一般的にエミュレートできる。基盤となるプラットフォームが演算を直接サポートしない場合、この分解は実装を導く テンプレートとして使用できる。
function sigmoid(builder, input) {
  return builder.div(
    builder.constant(input.dataType, 1),
    builder.add(
      builder.exp(builder.neg(input)), builder.constant(input.dataType, 1)));
}

8.9.47. slice

入力テンソルのsliceを生成する。
dictionary MLSliceOptions : MLOperatorOptions {
  sequence<[EnforceRange] unsigned long> strides;
};

partial interface MLGraphBuilder {
  MLOperand slice(MLOperand input,
                  sequence<[EnforceRange] unsigned long> starts,
                  sequence<[EnforceRange] unsigned long> sizes,
                  optional MLSliceOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits slice;
};

MLSliceOptions は次のメンバーを持つ:

strides, 型はsequence<[EnforceRange] unsigned long>

各axisに沿って各入力をstep overするstride。 strides配列の長さは入力テンソルのrankと等しくなければならない。 デフォルトは、すべて1からなるrank長の配列である。 例: 3-Dテンソルの場合は[1,1,1]。 Stridesは0より大きくなければならない。

引数:

戻り値: MLOperand。 各次元の指定された開始indexおよび終了indexにtensor値が切り詰められた、入力テンソルと同じrankの出力テンソル。

slice()のテンソル制限
オペランド 許可される データ型 許可されるランク
input 任意 N
output input同じ input同じ

MLOpSupportLimitsslice()について次のメンバーを持つ:

slice, 型はMLSingleInputSupportLimits

slice()演算子のサポート制限。

slice(input, starts, sizes, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. sizesitemsのいずれかが0である場合、 TypeErrorthrowする。

  4. startssizeおよびsizessizeの両方が inputrankと等しくない場合、TypeErrorthrowする。

  5. stridesを新しいlistとする。

  6. options.strides存在する場合:

    1. stridesoptions.stridesに設定する。

    2. stridessizeinputrankと等しくない場合、TypeErrorthrowする。

  7. inputShapeinputshapeとし、inputRankinputrankとする。

  8. outputShapeを新しいlistとする。

  9. 0からinputRankまで(含まない)の範囲内の各indexについて実行する:

    1. inputSizeinputShape[index]とする。

    2. inputSliceSizesizes[index]とする。

    3. strideを、空でない場合はstrides[index]、そうでない場合は1とする:

    4. inputSliceSizeが0の場合、TypeErrorthrowする。

      0-size dimensionsが許可される場合、これらの手順を改訂すること。[Issue #391]

    5. strideが1未満の場合、TypeErrorthrowする。

    6. starts[index]がinputSizeより大きい場合、TypeErrorthrowする。

    7. starts[index] + inputSliceSizeinputSizeより大きい場合、TypeErrorthrowする。

    8. outputSizeRoundingExcessを、inputSliceSize % stride != 0の場合は1、そうでない場合は0とする。

    9. outputSizeをfloor(inputSliceSize / stride) + outputSizeRoundingExcessとする:

    10. outputSizeoutputShapeappendする。

  10. outputDescを、inputdataTypeおよび outputShapeが与えられてMLOperandDescriptorを作成する結果とする。

  11. グラフ接続を作成する:

    1. outputを、outputDescが与えられてMLOperandを作成する結果とする。

    2. operatorを、startssizes、 およびoptionsが与えられた"slice"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. operatoroutputoutputに設定する。

  12. outputを返す。

8.9.48. softmax

指定されたaxisに沿って、N-D入力テンソルのsoftmax値を 計算する。
partial interface MLGraphBuilder {
  MLOperand softmax(MLOperand input,
                    [EnforceRange] unsigned long axis,
                    optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits softmax;
};
引数:

戻り値:

softmax()のテンソル制限
オペランド 許可される データ型 許可されるランク
input "float32", "float16" 1からNまで
output input同じ input同じ

MLOpSupportLimitssoftmax()について次のメンバーを持つ:

softmax, 型はMLSingleInputSupportLimits

softmax()演算子のサポート制限。

softmax(input, axis, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. inputdataTypeが(この表に従う) その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

  4. axisinputrank以上である場合、TypeErrorthrowする。

  5. グラフ接続を作成する:

    1. outputを、inputが与えられてMLOperandをcopyする結果とする。

    2. operatorを、axisおよびoptionsが与えられた"softmax"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. operatoroutputoutputに設定する。

  6. outputを返す。

この演算の振る舞いは、ユーザーエージェントは通常より効率的な実装を持つものの、次のように他の演算の使用から 一般的にエミュレートできる。基盤となるプラットフォームが演算を直接サポートしない場合、この分解は実装を導く テンプレートとして使用できる。
function softmax(builder, input, axis) {
  // This sample deploys a well-known implementation trick [1] to compute the
  // exponentials of the distances to the max value, instead of the exponentials
  // of the input values itself, in order to increase the numerical stability of
  // the result.
  // [1]: https://cs231n.github.io/linear-classify/#softmax
  const maxX = builder.reduceMax(input, {axes: [axis], keepDimensions: true});
  const expX = builder.exp(builder.sub(input, maxX));
  return builder.div(
    expX, builder.reduceSum(expX, {axes: [axis], keepDimensions: true}));
}

8.9.49. softplus

入力テンソルのsoftplus functionを 計算する。計算は式ln(1 + exp(x))に従う。
partial interface MLGraphBuilder {
  MLOperand softplus(MLOperand input, optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits softplus;
};
引数:

戻り値:

softplus()のテンソル制限
オペランド 許可される データ型 許可されるランク
input "float32", "float16" N
output input同じ input同じ

MLOpSupportLimitssoftplus()について次のメンバーを持つ:

softplus, 型はMLSingleInputSupportLimits

softplus()演算子のサポート制限。

softplus(input, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. inputdataTypeが(この表に従う) その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

  4. グラフ接続を作成する:

    1. outputを、inputが与えられてMLOperandをcopyする結果とする。

    2. operatorを、"softplus"演算およびoptions用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. operatoroutputoutputに設定する。

  5. outputを返す。

この演算の振る舞いは、ユーザーエージェントは通常より効率的な実装を持つものの、次のように他の演算の使用から 一般的にエミュレートできる。基盤となるプラットフォームが演算を直接サポートしない場合、この分解は実装を導く テンプレートとして使用できる。
function softplus(builder, input) {
  return builder.log(
    builder.add(builder.exp(input), builder.constant(input.dataType, 1)));
}

8.9.50. softsign

入力テンソルのsoftsign functionを 計算する。計算は式x / (1 + |x|)に従う。
partial interface MLGraphBuilder {
  MLOperand softsign(MLOperand input, optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits softsign;
};
この演算の振る舞いは、ユーザーエージェントは通常より効率的な実装を持つものの、次のように他の演算の使用から 一般的にエミュレートできる。基盤となるプラットフォームが演算を直接サポートしない場合、この分解は実装を導く テンプレートとして使用できる。
function softsign(builder, input) {
  return builder.div(
    input,
    builder.add(builder.constant(input.dataType, 1), builder.abs(input)));
}
引数:

戻り値:

softsign()のテンソル制限
オペランド 許可される データ型 許可されるランク
input "float32", "float16" N
output input同じ input同じ

MLOpSupportLimitssoftsign()について次のメンバーを持つ:

softsign, 型はMLSingleInputSupportLimits

softsign()演算子のサポート制限。

softsign(input, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. inputdataTypeが(この表に従う) その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

  4. グラフ接続を作成する:

    1. outputを、inputが与えられてMLOperandをcopyする結果とする。

    2. operatorを、"softsign"演算および options用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. operatoroutputoutputに設定する。

  5. outputを返す。

8.9.51. split

指定されたaxisに沿って、入力テンソルをいくつかのsub tensorsに分割する。
dictionary MLSplitOptions : MLOperatorOptions {
  [EnforceRange] unsigned long axis = 0;
};

partial interface MLGraphBuilder {
  sequence<MLOperand> split(
      MLOperand input,
      ([EnforceRange] unsigned long or sequence<[EnforceRange] unsigned long>) splits,
      optional MLSplitOptions options = {});
};

dictionary MLSplitSupportLimits {
  MLTensorLimits input;
  MLTensorLimits outputs;
};

partial dictionary MLOpSupportLimits {
  MLSplitSupportLimits split;
};
引数:

戻り値: sequence<MLOperand>。 分割された出力テンソル。splitsunsigned longの場合、 出力のsizesplitsと等しい。 各出力テンソルのshapeは、axisの 次元サイズが、inputaxisに沿った 次元サイズをsplitsで 割った商に等しいことを除き、inputと同じである。 splitssequence<unsigned long>の場合、 出力のsizesplitssizeと等しい。 i番目の出力テンソルのshapeは、axisに沿った 次元サイズがsplits[i]であることを除き、 inputと同じである。

MLSplitOptions は次のメンバーを持つ:

axis, 型はunsigned long、デフォルトは0

splitする次元。その値は、入力テンソルのrankをNとして、 [0, N-1]の範囲内でなければならない。

split()のテンソル制限
オペランド 許可される データ型 許可されるランク
input 任意 1からNまで
outputs input同じ input同じ

MLSplitSupportLimits は次のメンバーを持つ:

input, 型はMLTensorLimits

inputオペランド用のMLTensorLimits

outputs, 型はMLTensorLimits

すべてのoutputオペランド用のMLTensorLimits

MLOpSupportLimitssplit()について次のメンバーを持つ:

split, 型はMLSplitSupportLimits

split()演算子のサポート制限。

split(input, splits, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. axisoptions.axisとする。

  4. axisinputrank以上である場合、TypeErrorthrowする。

  5. splitsunsigned longである場合:

    1. splits有効なテンソル数でない場合、TypeErrorthrowする。

    2. inputshape[axis] % splitsが 0でない場合、TypeErrorthrowする。

    3. そうでない場合、splitCountsplitsとする。

  6. splitssequence<unsigned long>である場合:

    1. splitssize有効なテンソル数でない場合、TypeErrorthrowする。

    2. そのitemsのいずれかが0と等しい場合、TypeErrorthrowする。

      0-size dimensionsが許可される場合、上記の手順を改訂すること。[Issue #391]

    3. そのitemsの合計がinputshape[axis]と等しくない場合、TypeErrorthrowする。

    4. そうでない場合、splitCountsplitssizeとする。

  7. グラフ接続を作成する:

    1. operatorを、splitsおよびoptionsが与えられた "split"演算用の演算子とする。

    2. outputsを新しいlistとする。

    3. 0からsplitCountまで(含まない)の範囲内の各indexについて実行する:

      1. operandを、inputが与えられてMLOperandをcopyする結果とする。

      2. splitsunsigned longである場合、 newDimensionoperandshape[axis] / splitsとする。

      3. そうでない場合、newDimensionsplits[index]とする。

      4. operandshape[axis]を newDimensionに設定する。

      5. operand.[[operator]]operatorに設定する。

      6. operandoutputsappendする。

    4. operatorinputinputに設定する。

    5. operatoroutputsoutputsに設定する。

  8. outputsを返す。

この演算の振る舞いは、ユーザーエージェントは通常より効率的な実装を持つものの、次のように他の演算の使用から 一般的にエミュレートできる。基盤となるプラットフォームが演算を直接サポートしない場合、この分解は実装を導く テンプレートとして使用できる。
function split(builder, input, splits, options) {
  // This sample shows the case that the splits parameter is an array.
  const outputs = [];
  const inputShape = input.shape;
  const inputRank = inputShape.length;
  let starts = Array(inputRank).fill(0);
  let sizes = inputShape;
  let start = 0;
  for (const size of splits) {
    starts[options.axis] = start;
    sizes[options.axis] = size;
    outputs.push(builder.slice(input, starts, sizes));
    start += size;
  }
  return outputs;
}

8.9.52. tanh

入力テンソルのhyperbolic tangent functionを 計算する。計算は式(exp(2 * x) - 1) / (exp(2 * x) + 1)に従う。
partial interface MLGraphBuilder {
  MLOperand tanh(MLOperand input, optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits tanh;
};
引数:

戻り値:

tanh()のテンソル制限
オペランド 許可される データ型 許可されるランク
input "float32", "float16" N
output input同じ input同じ

MLOpSupportLimitstanh()について次のメンバーを持つ:

tanh, 型はMLSingleInputSupportLimits

tanh()演算子のサポート制限。

tanh(input, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. inputdataTypeが(この表に従う) その許可されるデータ型のいずれでもない場合、TypeErrorthrowする。

  4. グラフ接続を作成する:

    1. outputを、inputが与えられてMLOperandをcopyする結果とする。

    2. operatorを、optionsが与えられた"tanh"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. operatoroutputoutputに設定する。

  5. outputを返す。

この演算の振る舞いは、ユーザーエージェントは通常より効率的な実装を持つものの、次のように他の演算の使用から 一般的にエミュレートできる。基盤となるプラットフォームが演算を直接サポートしない場合、この分解は実装を導く テンプレートとして使用できる。
function tanh(builder, input) {
  return builder.div(
    builder.sub(
      builder.exp(builder.mul(builder.constant(input.dataType, 2), input)),
      builder.constant(input.dataType, 1)),
    builder.add(
      builder.exp(builder.mul(builder.constant(input.dataType, 2), input)),
      builder.constant(input.dataType, 1)));
}

8.9.53. tile

各次元に沿って、指定された回数だけテンソルを繰り返す。
partial interface MLGraphBuilder {
  MLOperand tile(MLOperand input,
                 sequence<unsigned long> repetitions,
                 optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits tile;
};
引数:

戻り値: MLOperand。 反転されたN-Dテンソル。

tile()のテンソル制限
オペランド 許可される データ型 許可されるランク
input 任意 N
output input同じ input同じ

MLOpSupportLimitstile()について次のメンバーを持つ:

tile, 型はMLSingleInputSupportLimits

tile()演算子のサポート制限。

tile(input, repetitions, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. repetitionssizeinputrankと等しくない場合、TypeErrorthrowする。

  4. repetitionsの値が0を含む場合、TypeErrorthrowする。

    0-size dimensionsが許可される場合、これらの手順を改訂すること。[Issue #391]

  5. outputShapeinputshapeのcopyとする。

  6. 0からoutputShapesizeまで(含まない)の範囲内の各indexについて実行する:

    1. outputShape[index]をoutputShape[index] * repetitions[index]に設定する。

  7. outputDescriptorを、inputdataTypeおよび outputShapeが与えられてMLOperandDescriptorを作成する結果とする。

  8. グラフ接続を作成する:

    1. outputを、outputDescriptorが与えられてMLOperandを作成する結果とする。

    2. operatorを、optionsが与えられた"tile"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. operatoroutputoutputに設定する。

  9. outputを返す。

8.9.54. transpose

permutationに従って入力テンソルの次元を置換する。
dictionary MLTransposeOptions : MLOperatorOptions {
  sequence<[EnforceRange] unsigned long> permutation;
};

partial interface MLGraphBuilder {
  MLOperand transpose(MLOperand input, optional MLTransposeOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits transpose;
};

MLTransposeOptions は次のメンバーを持つ:

permutation, 型は sequence<[EnforceRange] unsigned long>

出力shapeを置換するために使用される値。 デフォルトは[N-1, ..., 0]であり、ここでNは入力テンソルのrankである。例: 3-Dテンソルでは[2,1,0]。 これらのデフォルト値により、出力は入力の転置テンソルになる。指定された場合、 値の数は入力テンソルのrankと同じでなければならず、その値は重複なしで 0からN-1までの範囲内でなければならない。

引数:

戻り値: MLOperand。 置換または転置されたN-Dテンソル。

transpose()のテンソル制限
オペランド 許可される データ型 許可されるランク
input 任意 N
output input同じ input同じ

MLOpSupportLimitstranspose()について次のメンバーを持つ:

transpose, 型はMLSingleInputSupportLimits

transpose()演算子のサポート制限。

transpose(input, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. options.permutation存在しない場合、options.permutationinputshapeのすべてのindicesの逆順sequenceとする。

  4. そうでない場合、options.permutation存在する場合:

    1. そのsizeinputrankと 等しくない場合、TypeErrorthrowする。

    2. そのitemsが0からinputrankまで(含まない)の範囲内にない場合、 TypeErrorthrowする。

    3. 重複値を含む場合、TypeErrorthrowする。

  5. グラフ接続を作成する:

    1. outputを、inputが与えられてMLOperandをcopyする結果とする。

    2. operatorを、optionsが与えられた"transpose"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. operatoroutputoutputに設定する。

  6. outputを返す。

8.9.55. triangular

2-Dテンソル(matrix)が与えられた場合、入力テンソルの上三角部分または下三角部分のいずれかを含む2-Dテンソルを返す。 入力テンソルが2次元を超える場合、matricesのbatchとして扱われ、結果は同じshapeを持つ。
dictionary MLTriangularOptions : MLOperatorOptions {
  boolean upper = true;
  [EnforceRange] long diagonal = 0;
};

partial interface MLGraphBuilder {
  MLOperand triangular(MLOperand input, optional MLTriangularOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits triangular;
};

MLTriangularOptions は次のメンバーを持つ:

upper, 型はboolean、デフォルトはtrue

入力matrixの上部または下部のどちらを出力で保持するかを示す。Trueは上部を保持することを示す。

diagonal, 型はlong、デフォルトは0

入力matrixの主対角線の上または下にある対角線をいくつ保持または除外するかを指定する。 値0は、主対角線以外の対角線が影響を受けないことを意味する。

引数:

戻り値: MLOperand。 入力と同じshapeである、三角matrixまたはmatricesのbatchを表す出力テンソル。

triangular()のテンソル制限
オペランド 許可される データ型 許可されるランク
input 任意 2からNまで
output input同じ input同じ

MLOpSupportLimitstriangular()について次のメンバーを持つ:

triangular, 型はMLSingleInputSupportLimits

triangular()演算子のサポート制限。

triangular(input, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびinputとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. inputrankが(この表に従う)その許可されるランクのいずれでもない場合、TypeErrorthrowする。

  4. グラフ接続を作成する:

    1. outputを、inputが与えられてMLOperandをcopyする結果とする。

    2. operatorを、optionsが与えられた"triangular"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputinputに設定する。

    5. operatoroutputoutputに設定する。

  5. outputを返す。

triangularが異なるdiagonal設定でどのように動作するかの例。
// input:
//   [[7, 1, 2],
//    [9, 4, 8],
//    [2, 6, 3]]
const input = builder.constant(
  {dataType: 'float32', shape: [3, 3]},
  new Float32Array([7, 1, 2, 9, 4, 8, 2, 6, 3]));

// upper triangular matrix:
//   [[7, 1, 2],
//    [0, 4, 8],
//    [0, 0, 3]]
const upper = builder.triangular(input);

// upper triangular matrix with one additional set of diagonals excluded:
//   [[0, 1, 2],
//    [0, 0, 8],
//    [0, 0, 0]]
const upperPositive = builder.triangular(input, {diagonal: 1});

// upper triangular matrix with one additional set of diagonals retained:
//   [[7, 1, 2],
//    [9, 4, 8],
//    [0, 6, 3]]
const upperNegative = builder.triangular(input, {diagonal: -1});

// lower triangular matrix:
//   [[7, 0, 0],
//    [9, 4, 0],
//    [2, 6, 3]]
const lower = builder.triangular(input, {upper: false});

// lower triangular matrix with one additional set of diagonals retained:
//   [[7, 1, 0],
//    [9, 4, 8],
//    [2, 6, 3]]
const lowerPositive = builder.triangular(input, {upper: false, diagonal: 1});

// lower triangular matrix with one additional set of diagonals excluded:
//   [[0, 0, 0],
//    [9, 0, 0],
//    [2, 6, 0]]
const lowerNegative = builder.triangular(input, {upper: false, diagonal: -1})

// lower triangular matrix with two batches:
//   [[[7, 0, 0],
//     [9, 4, 0],
//     [2, 6, 3]],
//    [[1, 0, 0],
//     [4, 5, 0],
//     [7, 8, 9]]]
const lowerWithBatches = builder.triangular(input, {upper: false});

8.9.56. where

condition テンソルの対応する値に応じて、trueValue またはfalseValue テンソルから値を選択する。ここで非0はtrue、0はfalseである。condition テンソルは、element-wise logical operationsのいずれかの出力であることが多い。

この演算はbroadcast される。これは[numpy-broadcasting-rule]に従う。入力テンソルはbidirectionally broadcastableでなければならない。出力テンソルのrankは、入力テンソルの rankの最大値である。 出力テンソルの各次元について、そのサイズは入力テンソルのその次元に沿った最大サイズである。

partial interface MLGraphBuilder {
  MLOperand where(MLOperand condition,
                  MLOperand trueValue,
                  MLOperand falseValue,
                  optional MLOperatorOptions options = {});
};

dictionary MLWhereSupportLimits {
  MLTensorLimits condition;
  MLTensorLimits trueValue;
  MLTensorLimits falseValue;
  MLTensorLimits output;
};

partial dictionary MLOpSupportLimits {
  MLWhereSupportLimits where;
};
引数:

戻り値: MLOperandtrueValue またはfalseValue テンソルのいずれかからelement-wiseに選択された値を含む出力テンソル。

where()のテンソル制限
オペランド 許可される データ型 許可されるランク
condition "uint8" N
trueValue 任意 N
falseValue trueValue同じ N
output trueValue同じ N

MLWhereSupportLimits は次のメンバーを持つ:

condition, 型はMLTensorLimits

conditionオペランド用のMLTensorLimits

trueValue, 型はMLTensorLimits

trueValueオペランド用のMLTensorLimits

falseValue, 型はMLTensorLimits

falseValueオペランド用のMLTensorLimits

output, 型はMLTensorLimits

outputオペランド用のMLTensorLimits

MLOpSupportLimitswhere()について次のメンバーを持つ:

where, 型はMLWhereSupportLimits

where()演算子のサポート制限。

where(condition, trueValue, falseValue, options) メソッドの手順は次のとおりである:
  1. thisbuildできない場合、"InvalidStateError" DOMExceptionthrowする。

  2. オペランドを検証することをthisおよびconditiontrueValuefalseValueのいずれかとともに行った結果がfalseを返す場合、TypeErrorthrowする。

  3. conditiontrueValue、またはfalseValueのいずれかのdataTypeが(この表に従う) その許可されるデータ型のいずれでもない場合、 TypeErrorthrowする。

  4. outputShapeを、trueValueshapefalseValueshape双方向にbroadcastingする結果とする。

    1. それがfailureを返した場合、TypeErrorthrowする。

  5. outputShapeを、conditionshapeoutputShape双方向にbroadcastingする結果に設定する。

    1. それがfailureを返した場合、TypeErrorthrowする。

  6. descriptorを、trueValuedataTypeおよび outputShapeが与えられてMLOperandDescriptorを作成する結果とする。

  7. グラフ接続を作成する:

    1. outputを、thisおよび descriptorが与えられてMLOperandを作成する結果とする。

    2. operatorを、conditiontrueValuefalseValue、 およびoptionsが与えられた"where"演算用の演算子とする。

    3. output.[[operator]]operatorに設定する。

    4. operatorinputsconditiontrueValueおよびfalseValueに設定する。

    5. operatoroutputoutputに設定する。

  8. outputを返す。

この演算の振る舞いは、ユーザーエージェントは通常より効率的な実装を持つものの、次のように他の演算の使用から 一般的にエミュレートできる。基盤となるプラットフォームが演算を直接サポートしない場合、この分解は実装を導く テンプレートとして使用できる。
function where(builder, condition, trueValue, falseValue) {
  const c = builder.clamp(condition, {'minValue': 0, 'maxValue': 1});
  builder.add(
    builder.mul(trueValue, builder.cast(c, trueValue.dataType)),
    builder.mul(
      falseValue, builder.cast(builder.logicalNot(c), falseValue.dataType)));
}

9. アルゴリズム

9.1. ブロードキャスト

ブロードキャストは、 グラフ構築および計算中に、WebNNが異なるshapeを持つテンソルをどのように扱うかを説明する。これは[NumPy]の影響を強く受けており、[numpy-broadcasting-rule]に従う。おおまかに言えば、 小さいテンソルに対する演算を大きいテンソルのshape全体へ「broadcast」できるようにすることで、 copyを作らずに同じデータを繰り返し適用できるようにする。

最も単純な例は、add()mul() などのelement-wise二項演算で、スカラー定数をN次元テンソルに適用することである。 スカラー定数の複数のcopyを含む、一致するN次元テンソルを確保して埋める必要はなく、 これらのelement-wise演算ではスカラー定数を直接使用でき、スカラー値をN次元テンソル全体へ broadcastできる。次の考慮事項により、同じロジックは他の次元のテンソルにも適用される。

入力テンソルのshapeは互換でなければならない。あるテンソルは、最後(右端)の次元から開始して、 sizeが1であるaxisに沿ってそのテンソルを繰り返すか、新しい次元にまたがって繰り返すことで、 最初のテンソルを「引き伸ばせる」場合、別のテンソルへ一方向にbroadcast可能である。 例えば、[4]テンソルは、それを5回繰り返すことで[5, 4]テンソルへbroadcastできる。 [1]テンソルは、最後の次元で4回、前の次元で5回繰り返すことで[5,4]テンソルへbroadcastできる。 一方向ブロードキャストは、targetテンソルshapeが明示的に与えられるexpand() のような演算で重要である。

2つのテンソルは、最後の次元から開始して、それぞれのさまざまな次元にまたがって相互に 「引き伸ばせる」(繰り返せる)場合、双方向にbroadcast可能である。例えば、 [5,1]テンソルは、最初のテンソルを最後の次元で6回繰り返し、2つ目のテンソルを前の次元で5回 繰り返すことで、[1,6]テンソルと双方向にbroadcastできる。演算の結果は[5,6]テンソルになる。 双方向ブロードキャストはelement-wise演算に便利である。

すべての次元を整数倍でtargetテンソルのshapeへupsampleできる場合、テンソルはblockwise broadcast可能である。 例えば、[4,5]テンソルは、各要素を第1次元で4回、最後の次元で2回繰り返すことで、 正確な倍数(16 % 4 = 0、10 % 5 = 0)であるため、[16,10]テンソルへblockwise broadcastできる (例えば、最後の次元の値[1,2,3,4,5][1,1,2,2,3,3,4,4,5,5]へ繰り返される)。しかし、[4,5]テンソルは、 両方の次元で0でない余り(9 % 4 = 1、3 % 5 = 3)があるため、[9,3]テンソルとは互換でない。 Blockwise broadcastingは、memoryを節約するために大きなblockで共通の値を共有するのに有用である。 両方のテンソルは同じrankを持つことが期待され、出力shapeは単に、小さい方がupsampleされるtargetテンソルのshapeである。

一部の演算は、特別なsemanticsを持つブロードキャストを許可する。例えば、matmul() は入力テンソルの最後の2次元をmatrixの行および列として扱い、最初のmatrixの列数は2つ目のmatrixの行数と 等しくなければならない。行列乗算は、入力テンソルを乗算するmatricesのstackとして扱い、追加の任意の次元に またがって双方向にbroadcastされる。

shapeFromおよびshapeToのshapeを 一方向にbroadcastするには、次の手順を実行する。 shapeFromおよびshapeToは、テンソルの次元を表す正の整数のlistであり、 この手順は正の整数の新しいlist、 またはfailureを返す。
  1. sizeFromshapeFromsizeとする。

  2. sizeToshapeTosizeとする。

  3. sizeFrom > sizeToの場合、failureを返す。

  4. paddedShapeFromshapeFromcloneとする。

  5. paddedShapeFromsizesizeToより小さい間、paddedShapeFromに1をprependする。

  6. outputShapeを新しいlistとする。

  7. 0からsizeToまで(含まない)の範囲内の各indexについて実行する:

    1. dimFrompaddedShapeFrom[index]とする。

    2. dimToshapeTo[index]とする。

    3. dimTodimFromと等しくなく、かつdimFromが1と等しくない場合、 failureを返す。

    4. dimTooutputShapeAppendする。

  8. outputShapeを返す。

shapeFromおよびshapeTo一方向にbroadcastingすることがfailureにならない場合、 shapeFromshapeTo一方向にbroadcast可能である。

shapeAおよびshapeBのshapeを 双方向にbroadcastするには、次の手順を実行する。 shapeAおよびshapeBは、テンソルの次元を表す正の整数のlistであり、 この手順は正の整数の新しいlist、 またはfailureを返す。
  1. sizeAshapeAsizeとする。

  2. sizeBshapeBsizeとする。

  3. outputSizesizeAおよびsizeBの最大値とする。

  4. paddedAshapeAcloneとする。

  5. paddedAsizeoutputSizeより小さい間、paddedAに1をprependする。

  6. paddedBshapeBcloneとする。

  7. paddedBsizeoutputSizeより小さい間、paddedBに1をprependする。

  8. outputShapeを新しいlistとする。

  9. 0からoutputSizeまで(含まない)の範囲内の各indexについて実行する:

    1. dimApaddedA[index]とする。

    2. dimBpaddedB[index]とする。

    3. dimAdimBと等しくなく、かつdimAが1と等しくなく、 かつdimBが1と等しくない場合、failureを返す。

    4. dimAおよびdimBの最大値をoutputShapeAppendする。

  10. outputShapeを返す。

shapeAおよびshapeB双方向にbroadcastingすることがfailureにならない場合、 shapeAshapeB双方向にbroadcast可能である。

shapeFromおよびshapeToのshapeを blockwise broadcastするには、次の手順を実行する。 shapeFromおよびshapeToは、テンソルの次元を表す正の整数のlistであり、 この手順はtrueまたはfalseを返す。
  1. shapeFromsizeshapeTosizeと等しくない場合、falseを返す。

  2. 0からshapeTosizeまで(含まない)の範囲内の各indexについて実行する:

    1. shapeFrom[index]がshapeTo[index]を 正確に割り切らない場合、falseを返す。

  3. trueを返す。

shapeFromおよびshapeToblockwise broadcastingすることがtrueを返す場合、shapeFromshapeToblockwise broadcast可能である。

9.2. Casting

明示的な数値castingは、MLNumber またはdouble として渡されたパラメーターを、入力または出力MLOperandMLOperandDataType に一致するように変換する必要があるアルゴリズムで使用される。

数値xを与えられたMLOperandDataType dataTypecastするには、 次の手順を実行する。これらは数値を返す。
  1. dataTypeでswitchする:

    "float32"

    ConvertToFloat(x, 32)を返す。

    "float16"

    ConvertToFloat(x, 16)を返す。

    "int64"

    ConvertToInt(x, 64, "signed")を返す。

    "uint64"

    ConvertToInt(x, 64, "unsigned")を返す。

    "int32"

    ConvertToInt(x, 32, "signed")を返す。

    "uint32"

    ConvertToInt(x, 32, "signed")を返す。

    "int8"

    ConvertToInt(x, 8, "signed")を返す。

    "uint8"

    ConvertToInt(x, 8, "unsigned")を返す。

注記: castへの入力は、無制限の範囲と精度を持つ抽象数値であり、 special valuesであるInfinity、-InfinityおよびNaNを含む。出力も抽象数値であるが、指定された型として正確に表現可能である。

ConvertToFloat(x, bitLength)の手順は次のとおりである:
  1. xがNaNである場合、NaNを返す。

  2. bitLengthでswitchする:

    32
    1. upperBoundを2128とする。

    2. lowerBoundを-2128とする。

    3. Sを、-0を除く[IEEE-754-2019] binary32浮動小数点値の集合とする。ただしspecial valuesである upperBoundおよびlowerBoundを追加する。

    16
    1. upperBoundを216とする。

    2. lowerBoundを-216とする。

    3. Sを、-0を除く[IEEE-754-2019] binary16浮動小数点値の集合とする。ただしspecial valuesである upperBoundおよびlowerBoundを追加する。

  3. yを、S内でxに最も近い数値とする。2つの等しく近い値がある場合は、 significandが偶数である数値を選択する。この目的のため、2つのspecial values lowerBoundおよびupperBoundは偶数のsignificandsを持つと見なされる。

  4. yupperBoundである場合、+Infinityを返す。

  5. ylowerBoundである場合、-Infinityを返す。

  6. yが+0であり、xが負である場合、-0を返す。

  7. yを返す。

注記: これは[WEBIDL]の定義に基づくが、 16-bit浮動小数点値をcoverするように拡張されている。

ConvertToInt(x, bitLength, signedness) の手順は次のとおりである:
  1. signednessが"unsigned"である場合:

    1. lowerBoundを0とする。

    2. upperBoundを2bitLength - 1とする。

  2. そうでない場合:

    1. lowerBoundを-(2bitLength - 1)とする。

    2. upperBoundを2bitLength - 1 - 1とする。

  3. xが-0である場合、xを+0に設定する。

  4. xがNaNである場合、+0を返す。

  5. xをmin(max(x, lowerBound), upperBound)に設定する。

  6. xを最も近い整数へroundし、2つの整数のちょうど中間にある場合は偶数の整数を選択し、 -0ではなく+0を選択する。

  7. xを返す。

注記: これは[WEBIDL]の定義に基づくが、 次の違いがある: 64-bit整数は特別に扱われず、入力xは抽象数値であり、clampingは常に実行される。

9.3. その他

list Aは、AsizeBsizeと等しく、 A内の各itemB内の同じindexにあるitemと等しい場合、 list B等しい

[INFRA]に定義が利用可能になったら、これを削除すること。[whatwg/infra Issue #664]

10.

次のbuild graphが与えられた場合:
constant1 ---+
             +--- Add ---> intermediateOutput1 ---+
input1    ---+                                    |
                                                  +--- Mul---> output
constant2 ---+                                    |
             +--- Add ---> intermediateOutput2 ---+
input2    ---+
次のcodeはこのgraphを実装する:
// Use tensors in 4 dimensions.
const TENSOR_SHAPE = [1, 2, 2, 2];
const TENSOR_SIZE = 8;

const context = await navigator.ml.createContext();
const builder = new MLGraphBuilder(context);

// Create MLOperandDescriptor object.
const desc = {
  dataType: 'float32',
  shape: TENSOR_SHAPE
};

// constant1 is a constant MLOperand with the value 0.5.
const constantBuffer1 = new Float32Array(TENSOR_SIZE).fill(0.5);
const constant1 = builder.constant(desc, constantBuffer1);

// input1 is one of the input MLOperands. Its value will be set before
// execution.
const input1 = builder.input('input1', desc);

// constant2 is another constant MLOperand with the value 0.5.
const constantBuffer2 = new Float32Array(TENSOR_SIZE).fill(0.5);
const constant2 = builder.constant(desc, constantBuffer2);

// input2 is another input MLOperand. Its value will be set before execution.
const input2 = builder.input('input2', desc);

// intermediateOutput1 is the output of the first Add operation.
const intermediateOutput1 = builder.add(constant1, input1);

// intermediateOutput2 is the output of the second Add operation.
const intermediateOutput2 = builder.add(constant2, input2);

// output is the output MLOperand of the Mul operation.
const output = builder.mul(intermediateOutput1, intermediateOutput2);

11. 演算子エミュレーション

このsectionは非規範的である。

他のneural network inference APIに存在する演算は、多くの場合、WebNNに存在する演算を使用してemulateできる。

11.1. squeeze

squeeze演算は、 size 1である入力の指定されたすべての次元を削除したテンソルを返す。これは、次のようにreshape() 演算を使用して一般的に実装できる:
function squeeze(builder, input, axes) {
  if (!axes)
    axes = [];
  if (!axes.length)
    input.shape.forEach((item, i) => {
      axes.push(i);
    });
  const shape = Array.from(input.shape);
  for (let axis of axes.sort().reverse())
    if (axis < shape.length && shape[axis] == 1)
      shape.splice(axis, 1);
  return builder.reshape(input, shape);
}

11.2. unsqueeze

unsqueeze演算は、 指定された位置にsize 1の次元が挿入された新しいテンソルを返す。これは、次のようにreshape() 演算を使用して一般的に実装できる:
function unsqueeze(builder, input, axes) {
  const shape = Array.from(input.shape);
  for (let axis of axes.sort())
    shape.splice(axis, 0, 1);
  return builder.reshape(input, shape);
}

11.3. flatten

flatten演算は、 入力を1次元テンソルにreshapeする。これは、次のようにreshape() 演算を使用して一般的に実装できる:
function flatten(builder, input, axis) {
  if (axis > input.shape.length)
    return input;
  const before = axis.slice(0, axis).reduce((a, b) => a * b, 1);
  const after = axis.slice(axis, input.shape.length).reduce((a, b) => a * b, 1);
  return builder.reshape(input, [before, after]);
}

12. 付録

12.1. MLOperandDataTypeArrayBufferView の互換性

MLOperandDataType ArrayBufferView
float32 Float32Array
float16 Float16Array
int64 BigInt64Array
uint64 BigUint64Array
int32 Int32Array
uint32 Uint32Array
int8 Int8Array
uint8 Uint8Array

Float16ArrayECMA Stage 3にあり、そのdesignが完了していることを示している。 native implementationsに先立ってこの型を有効にしたい実装者は、Uint16Array を介してraw bitsを渡すことにより、この型をemulateできる。 [Issue webnn#373]

13. 謝辞

この仕様はAndroid Neural Networks API C APIの概念に従っている。

use casesについて、Tomoyuki Shimizu、Ningxin Hu、Zhiqiang YuおよびBelem Zhangに感謝する。

API仕様への貢献について、Nikhil Thorat、Daniel Smilkov、Ganesan Ramalingam、Rafael Cintronおよび Benjamin Poulainに感謝する。

web architecture fit、design consistencyおよびdeveloper ergonomicsについてこの仕様をreviewしてくれた Sangwhan MoonおよびW3C Technical Architecture Groupに感謝する。

アルゴリズムを追加し、この仕様のnavigationを快適な体験にしてくれたZoltan Kisに感謝する。 仕様をmodern editorial conventionsに合わせてくれたJoshua Bellに感謝する。注意深いreviewおよびcommentsについて、 Ningxin Hu、Lisha Guo、Shiyi Zou、Mingming Xu、Junwei Fu、Bruce DaiおよびBin Miaoに感謝する。

privacy and security reviewおよびfeedbackについて、W3C Privacy Interest Groupに感謝する。

security reviewおよびquestionsについて、Alex GoughおよびChrome Security teamに感謝する。

ONNXからの実践的なguidelinesおよびlearningsを共有してくれたMichal Karzynskiに感謝する。

feedbackおよびprivacy considerationsについて、Kaustubha GovindおよびChrome privacy reviewersに感謝する。

Chromium implementation reviewおよびfeedbackについて、Jiewei Qianに感謝する。

transformer supportの調査およびrecommendationの提供に関する作業について、Dwayne Robinson、Joshua LochnerおよびWanming Linに感謝する。 operator conformanceおよびweb-platform-tests implementationのreviewsを提供してくれたDwayneおよびWanmingにも追加で感謝する。

web-platform-testsを仕様とともに進化させ続ける継続的な貢献について、Feng Daiに感謝する。

reviewsおよびsuggestionsについて、Fuqiao XueおよびW3C Internationalization Activityに感謝する。

14. 変更

このsectionは非規範的である。

このsectionは、Classes of Changesに基づき、 前回のmajor publication以降にこの仕様へ行われた変更を記録する。

Candidate Recommendation Snapshot 11 April 202422 January 2026の間の詳細な変更

新機能(class 4

新機能を追加しないその他の変更(class 3

文書の解釈に機能的な影響を与えない変更(class 2

Horizontal(class 2およびclass 3

Editorial(class 2

適合性

文書の 慣例

適合性要件は、記述的な表明と RFC 2119 の用語を組み合わせて表現される。 この文書の規範的な部分におけるキーワード “MUST”, “MUST NOT”, “REQUIRED”, “SHALL”, “SHALL NOT”, “SHOULD”, “SHOULD NOT”, “RECOMMENDED”, “MAY”, および “OPTIONAL” は、 RFC 2119 で説明されているとおりに解釈される。 ただし、可読性のため、 これらの語はこの仕様ではすべて大文字では表記されない。

この仕様のすべてのテキストは、 明示的に非規範的と記されたsection、例、および注記を除き、規範的である。[RFC2119]

この仕様の例は、“for example” という語で導入されるか、 または規範的テキストから class="example" によって区別される。 例えば次のように:

これは情報提供的な例の一例である。

情報提供的な注記は “Note” という語で始まり、 規範的テキストから class="note" によって区別される。 例えば次のように:

Note, これは情報提供的な注記である。

適合 アルゴリズム

アルゴリズムの一部として命令形で表現される要件 (例えば "strip any leading space characters" または "return false and abort these steps" など)は、 そのアルゴリズムを導入する際に用いられたキーワード ("must", "should", "may" など)の意味で解釈される。

アルゴリズムまたは具体的な手順として表現された適合性要件は、 最終結果が等価である限り、 任意の方法で実装できる。 特に、この仕様で定義されるアルゴリズムは 理解しやすいことを意図しており、 performantであることを意図していない。 実装者には最適化が推奨される。

索引

この仕様で定義される用語

参照により定義される用語

参考文献

規範的参考文献

[ECMASCRIPT]
ECMAScript Language Specification. URL: https://tc39.es/ecma262/multipage/
[HTML]
Anne van Kesteren; et al. HTML Standard. Living Standard. URL: https://html.spec.whatwg.org/multipage/
[INFRA]
Anne van Kesteren; Domenic Denicola. Infra Standard. Living Standard. URL: https://infra.spec.whatwg.org/
[NUMPY-BROADCASTING-RULE]
The SciPy community. General Broadcasting Rules of NumPy. July 2019. URL: https://numpy.org/doc/stable/user/basics.broadcasting.html#general-broadcasting-rules
[PERMISSIONS-POLICY-1]
Ian Clelland. Permissions Policy. 6 October 2025. WD. URL: https://www.w3.org/TR/permissions-policy-1/
[RFC2119]
S. Bradner. Key words for use in RFCs to Indicate Requirement Levels. March 1997. Best Current Practice. URL: https://datatracker.ietf.org/doc/html/rfc2119
[WEBGPU]
Kai Ninomiya; Brandon Jones; Jim Blandy. WebGPU. 12 May 2026. CRD. URL: https://www.w3.org/TR/webgpu/
[WEBIDL]
Edgar Chen; Timothy Gu. Web IDL Standard. Living Standard. URL: https://webidl.spec.whatwg.org/

非規範的参考文献

[Batch-Normalization]
Sergey Ioffe; Christian Szegedy. Batch Normalization: Accelerating Deep Network Training by Reducing Internal Covariate Shift. March 2015. URL: https://arxiv.org/abs/1502.03167
[ContextualLoss]
Roey Mechrez; Itamar Talmi; Lihi Zelnik-Manor. The Contextual Loss for Image Transformation with Non-Aligned Data. July 2018. URL: https://arxiv.org/abs/1803.02077
[DeepLabv3+]
Liang-Chieh Chen; et al. Encoder-Decoder with Atrous Separable Convolution for Semantic Image Segmentation. August 2018. URL: https://arxiv.org/abs/1802.02611
[DeepMoji]
Bjarke Felbo; et al. Using millions of emoji occurrences to learn any-domain representations for detecting sentiment, emotion and sarcasm. October 2017. URL: https://arxiv.org/abs/1708.00524
[ELU]
Djork-Arné Clevert; Thomas Unterthiner; Sepp Hochreiter. Fast and Accurate Deep Network Learning by Exponential Linear Units (ELUs). February 2016. URL: https://arxiv.org/abs/1511.07289
[Error-Function]
Larry C. Andrews. Special functions of mathematics for engineers. 1998. URL: https://books.google.com/books?id=2CAqsF-RebgC&pg=PA110
[FaceForensics++]
Andreas Rössler; et al. FaceForensics++. January 2019. URL: https://github.com/ondyari/FaceForensics
[FaceNet]
Florian Schroff; Dmitry Kalenichenko; James Philbin. FaceNet: A Unified Embedding for Face Recognition and Clustering. June 2015. URL: https://arxiv.org/abs/1503.03832
[FAN]
Adrian Bulat; Georgios Tzimiropoulos. How far are we from solving the 2D & 3D Face Alignment problem? (and a dataset of 230,000 3D facial landmarks). September 2017. URL: https://arxiv.org/abs/1703.07332
[GNMT]
Minh-Thang Luong; Eugene Brevdo; Rui Zhao. Neural Machine Translation (seq2seq) Tutorial. May 2017. URL: https://github.com/tensorflow/nmt
[GPT2]
Alec Radford; et al. Language Models are Unsupervised Multitask Learners. February 2019. URL: https://d4mucfpksywv.cloudfront.net/better-language-models/language-models.pdf
[GRU]
Kyunghyun Cho; et al. Learning Phrase Representations using RNN Encoder–Decoder for Statistical Machine Translation. September 2014. URL: https://arxiv.org/pdf/1406.1078.pdf
[HR-TIME-3]
Yoav Weiss. High Resolution Time. 24 March 2026. WD. URL: https://www.w3.org/TR/hr-time-3/
[IEEE-754-2019]
IEEE Standard for Floating-Point Arithmetic. 22 July 2019. URL: https://ieeexplore.ieee.org/document/8766229
[IM2TXT]
Oriol Vinyals; et al. Show and Tell: Lessons learned from the 2015 MSCOCO Image Captioning Challenge. September 2016. URL: https://arxiv.org/abs/1609.06647
[Instance-Normalization]
Dmitry Ulyanov; Andrea Vedaldi; Victor Lempitsky. Instance Normalization: The Missing Ingredient for Fast Stylization. July 2016. URL: https://arxiv.org/abs/1607.08022
[Layer-Normalization]
Jimmy Lei Ba; Jamie Ryan Kiros; Geoffrey E. Hinton. Layer Normalization. July 2016. URL: https://arxiv.org/abs/1607.06450
[LDM]
Robin Rombach; et al. High-Resolution Image Synthesis with Latent Diffusion Models. April 2022. URL: https://arxiv.org/abs/2112.10752
[LeakyReLU]
Andrew L. Maas; Awni Y. Hannun; Andrew Y. Ng. Rectifier Nonlinearities Improve Neural Network Acoustic Models. June 2013. URL: https://pdfs.semanticscholar.org/367f/2c63a6f6a10b3b64b8729d601e69337ee3cc.pdf
[LLAMA-2-7B]
Hugo Touvron; et al. Llama 2: Open Foundation and Fine-Tuned Chat Models. July 2023. URL: https://arxiv.org/abs/2307.09288
[LSTM]
Sepp Hochreiter; Jürgen Schmidhuber. Long Short-Term Memory. November 1997. URL: https://doi.org/10.1162/neco.1997.9.8.1735
[m2m100_418M]
Angela Fan; et al. Beyond English-Centric Multilingual Machine Translation. October 2020. URL: https://arxiv.org/abs/2010.11125
[MaskR-CNN]
Kaiming He; et al. Mask R-CNN. January 2018. URL: https://arxiv.org/abs/1703.06870
[MobileNetV3]
Andrew Howard; et al. Searching for MobileNetV3. November 2019. URL: https://arxiv.org/pdf/1905.02244
[MODELS]
Machine Learning for the Web Community Group. The first-wave models. 2020. URL: https://github.com/webmachinelearning/webnn/blob/master/op_compatibility/first_wave_models.md
[NumPy]
The SciPy community. NumPy. July 2019. URL: https://numpy.org/doc/stable/
[OpenNMT]
Guillaume Klein; et al. OpenNMT: Open-Source Toolkit for Neural Machine Translation. March 2017. URL: https://arxiv.org/abs/1701.02810
[PairedCycleGAN]
Huiwen Chang; et al. PairedCycleGAN: Asymmetric Style Transfer for Applying and Removing Makeup. June 2018. URL: http://openaccess.thecvf.com/content_cvpr_2018/html/Chang_PairedCycleGAN_Asymmetric_Style_CVPR_2018_paper.html
[PoseNet]
Dan Oved. Real-time Human Pose Estimation in the Browser with TensorFlow.js. May 2018. URL: https://medium.com/tensorflow/real-time-human-pose-estimation-in-the-browser-with-tensorflow-js-7dd0bc881cd5
[POWERFUL-FEATURES]
Mike West. Secure Contexts. 10 November 2023. CRD. URL: https://www.w3.org/TR/secure-contexts/
[Prefix-sum]
The Wikipedia community. Prefix Sum. January 2025. URL: https://en.wikipedia.org/wiki/Prefix_sum
[RNNoise]
Jean-Marc Valin. Recurrent neural network for audio noise reduction. September 2017. URL: https://github.com/xiph/rnnoise
[SECURITY-PRIVACY-QUESTIONNAIRE]
Theresa O'Connor; Peter Snyder; Simone Onofri. Self-Review Questionnaire: Security and Privacy. 18 April 2025. NOTE. URL: https://www.w3.org/TR/security-privacy-questionnaire/
[SegAny]
Alexander Kirillov; et al. Segment Anything. April 2023. URL: https://arxiv.org/abs/2304.02643
[SRGAN]
Christian Ledig; et al. Photo-Realistic Single Image Super-Resolution Using a Generative Adversarial Network. May 2017. URL: https://arxiv.org/abs/1609.04802
[SSD]
Wei Liu; et al. SSD: Single Shot MultiBox Detector. December 2016. URL: https://arxiv.org/abs/1512.02325
[T5-SMALL]
Colin Raffel; et al. Exploring the Limits of Transfer Learning with a Unified Text-to-Text Transformer. June 2020. URL: https://jmlr.org/papers/volume21/20-074/20-074.pdf
[UTR36]
Mark Davis; Michel Suignard. Unicode Security Considerations. 19 September 2014. Unicode Technical Report #36. URL: https://www.unicode.org/reports/tr36/tr36-15.html
[UTS55]
Robin Leroy; Mark Davis. Unicode Source Code Handling. 29 January 2024. Unicode Technical Standard #55. URL: https://www.unicode.org/reports/tr55/tr55-5.html
[Video-Summarization-with-LSTM]
Ke Zhang; et al. Video summarization with long short-term memory. October 2016. URL: http://www-scf.usc.edu/~zhan355/ke_eccv2016.pdf
[WASM-JS-API-2]
. Ms2ger; Ryan Hunt. WebAssembly JavaScript Interface. 14 May 2026. CRD. URL: https://www.w3.org/TR/wasm-js-api-2/
[WCAG]
Michael Cooper; et al. Web Content Accessibility Guidelines (WCAG) 2.2. 12 December 2024. REC. URL: https://www.w3.org/TR/WCAG22/
[WEBMACHINELEARNING-ETHICS]
Anssi Kostiainen. Ethical Principles for Web Machine Learning. 8 January 2024. DNOTE. URL: https://www.w3.org/TR/webmachinelearning-ethics/
[Whisper]
Alec Radford; et al. Robust Speech Recognition via Large-Scale Weak Supervision. December 2022. URL: https://arxiv.org/abs/2212.04356
[YOLO]
Joseph Redmon; et al. You Only Look Once: Unified, Real-Time Object Detection. May 2016. URL: https://arxiv.org/abs/1506.02640

IDL 索引

interface mixin NavigatorML {
  [SecureContext, SameObject] readonly attribute ML ml;
};
Navigator includes NavigatorML;
WorkerNavigator includes NavigatorML;

enum MLPowerPreference {
  "default",
  "high-performance",
  "low-power"
};

dictionary MLContextOptions {
  MLPowerPreference powerPreference = "default";
  boolean accelerated = true;
};

[SecureContext, Exposed=(Window, Worker)]
interface ML {
  Promise<MLContext> createContext(optional MLContextOptions options = {});
  Promise<MLContext> createContext(GPUDevice gpuDevice);
};

typedef record<USVString, MLTensor> MLNamedTensors;

dictionary MLContextLostInfo {
  DOMString message;
};

[SecureContext, Exposed=(Window, Worker)]
interface MLContext {
  undefined dispatch(MLGraph graph, MLNamedTensors inputs, MLNamedTensors outputs);

  Promise<MLTensor> createTensor(MLTensorDescriptor descriptor);
  Promise<MLTensor> createConstantTensor(
    MLOperandDescriptor descriptor, AllowSharedBufferSource inputData);

  Promise<ArrayBuffer> readTensor(MLTensor tensor);
  Promise<undefined> readTensor(MLTensor tensor, AllowSharedBufferSource outputData);

  undefined writeTensor(MLTensor tensor, AllowSharedBufferSource inputData);

  MLOpSupportLimits opSupportLimits();

  undefined destroy();

  readonly attribute boolean accelerated;
  readonly attribute Promise<MLContextLostInfo> lost;
};

dictionary MLOpSupportLimits {
  MLInputOperandLayout preferredInputLayout;
  [EnforceRange] unsigned long long maxTensorByteLength;
  MLTensorLimits input;
  MLTensorLimits constant;
  MLTensorLimits output;
};

dictionary MLRankRange {
  unsigned long min;
  unsigned long max;
};

typedef sequence<MLOperandDataType> MLDataTypeList;

dictionary MLTensorLimits {
  MLDataTypeList dataTypes;
  MLRankRange rankRange;
};

dictionary MLBinarySupportLimits {
  MLTensorLimits a;
  MLTensorLimits b;
  MLTensorLimits output;
};

dictionary MLSingleInputSupportLimits {
  MLTensorLimits input;
  MLTensorLimits output;
};

[SecureContext, Exposed=(Window, Worker)]
interface MLGraph {
  undefined destroy();
};

enum MLInputOperandLayout {
  "nchw",
  "nhwc"
};

enum MLOperandDataType {
  "float32",
  "float16",
  "int32",
  "uint32",
  "int64",
  "uint64",
  "int8",
  "uint8"
};

dictionary MLOperandDescriptor {
  required MLOperandDataType dataType;
  required sequence<[EnforceRange] unsigned long> shape;
};

[SecureContext, Exposed=(Window, Worker)]
interface MLOperand {
  readonly attribute MLOperandDataType dataType;
  readonly attribute FrozenArray<unsigned long> shape;
};

dictionary MLOperatorOptions {
  USVString label = "";
};

typedef (bigint or unrestricted double) MLNumber;

dictionary MLTensorDescriptor : MLOperandDescriptor {
  boolean readable = false;
  boolean writable = false;
};

[SecureContext, Exposed=(Window, Worker)]
interface MLTensor {
  readonly attribute MLOperandDataType dataType;
  readonly attribute FrozenArray<unsigned long> shape;
  readonly attribute boolean readable;
  readonly attribute boolean writable;
  readonly attribute boolean constant;

  undefined destroy();
};

typedef record<USVString, MLOperand> MLNamedOperands;

[SecureContext, Exposed=(Window, Worker)]
interface MLGraphBuilder {
  // Construct the graph builder from the context.
  constructor(MLContext context);

  // Create an operand for a graph input.
  MLOperand input(USVString name, MLOperandDescriptor descriptor);

  // Create an operand for a graph constant.
  MLOperand constant(MLOperandDescriptor descriptor,
                     AllowSharedBufferSource buffer);

  // Create a scalar operand from the specified number of the specified type.
  MLOperand constant(MLOperandDataType dataType, MLNumber value);

  // Create an operand from a specified constant tensor.
  MLOperand constant(MLTensor tensor);

  // Compile the graph up to the specified output operands asynchronously.
  Promise<MLGraph> build(MLNamedOperands outputs);
};

dictionary MLArgMinMaxOptions : MLOperatorOptions {
  boolean keepDimensions = false;
  MLOperandDataType outputDataType = "int32";
};

partial interface MLGraphBuilder {
  MLOperand argMin(MLOperand input, [EnforceRange] unsigned long axis,
                   optional MLArgMinMaxOptions options = {});
  MLOperand argMax(MLOperand input, [EnforceRange] unsigned long axis,
                   optional MLArgMinMaxOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits argMin;
  MLSingleInputSupportLimits argMax;
};

dictionary MLBatchNormalizationOptions : MLOperatorOptions {
  MLOperand scale;
  MLOperand bias;
  [EnforceRange] unsigned long axis = 1;
  double epsilon = 1e-5;
};

partial interface MLGraphBuilder {
  MLOperand batchNormalization(MLOperand input, MLOperand mean, MLOperand variance,
                               optional MLBatchNormalizationOptions options = {});
};

dictionary MLBatchNormalizationSupportLimits {
  MLTensorLimits input;
  MLTensorLimits mean;
  MLTensorLimits variance;
  MLTensorLimits scale;
  MLTensorLimits bias;
  MLTensorLimits output;
};

partial dictionary MLOpSupportLimits {
  MLBatchNormalizationSupportLimits batchNormalization;
};

partial interface MLGraphBuilder {
  MLOperand cast(MLOperand input,
                 MLOperandDataType dataType,
                 optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits cast;
};

dictionary MLClampOptions : MLOperatorOptions {
  MLNumber minValue;
  MLNumber maxValue;
};

partial interface MLGraphBuilder {
  MLOperand clamp(MLOperand input, optional MLClampOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits clamp;
};

partial interface MLGraphBuilder {
  MLOperand concat(sequence<MLOperand> inputs,
                   [EnforceRange] unsigned long axis,
                   optional MLOperatorOptions options = {});
};

dictionary MLConcatSupportLimits {
  MLTensorLimits inputs;
  MLTensorLimits output;
};

partial dictionary MLOpSupportLimits {
  MLConcatSupportLimits concat;
};

enum MLConv2dFilterOperandLayout {
  "oihw",
  "hwio",
  "ohwi",
  "ihwo"
};

dictionary MLConv2dOptions : MLOperatorOptions {
  sequence<[EnforceRange] unsigned long> padding;
  sequence<[EnforceRange] unsigned long> strides;
  sequence<[EnforceRange] unsigned long> dilations;
  [EnforceRange] unsigned long groups = 1;
  MLInputOperandLayout inputLayout = "nchw";
  MLConv2dFilterOperandLayout filterLayout = "oihw";
  MLOperand bias;
};

partial interface MLGraphBuilder {
  MLOperand conv2d(MLOperand input,
                   MLOperand filter,
                   optional MLConv2dOptions options = {});
};

dictionary MLConv2dSupportLimits {
  MLTensorLimits input;
  MLTensorLimits filter;
  MLTensorLimits bias;
  MLTensorLimits output;
};

partial dictionary MLOpSupportLimits {
  MLConv2dSupportLimits conv2d;
};

enum MLConvTranspose2dFilterOperandLayout {
  "iohw",
  "hwoi",
  "ohwi"
};

dictionary MLConvTranspose2dOptions : MLOperatorOptions {
  sequence<[EnforceRange] unsigned long> padding;
  sequence<[EnforceRange] unsigned long> strides;
  sequence<[EnforceRange] unsigned long> dilations;
  sequence<[EnforceRange] unsigned long> outputPadding;
  sequence<[EnforceRange] unsigned long> outputSizes;
  [EnforceRange] unsigned long groups = 1;
  MLInputOperandLayout inputLayout = "nchw";
  MLConvTranspose2dFilterOperandLayout filterLayout = "iohw";
  MLOperand bias;
};

partial interface MLGraphBuilder {
  MLOperand convTranspose2d(MLOperand input, MLOperand filter,
                            optional MLConvTranspose2dOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLConv2dSupportLimits convTranspose2d;
};

dictionary MLCumulativeSumOptions : MLOperatorOptions {
  boolean exclusive = false;
  boolean reversed = false;
};

partial interface MLGraphBuilder {
  MLOperand cumulativeSum(MLOperand input,
                          unsigned long axis,
                          optional MLCumulativeSumOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits cumulativeSum;
};

partial interface MLGraphBuilder {
  MLOperand add(MLOperand a, MLOperand b, optional MLOperatorOptions options = {});
  MLOperand sub(MLOperand a, MLOperand b, optional MLOperatorOptions options = {});
  MLOperand mul(MLOperand a, MLOperand b, optional MLOperatorOptions options = {});
  MLOperand div(MLOperand a, MLOperand b, optional MLOperatorOptions options = {});
  MLOperand max(MLOperand a, MLOperand b, optional MLOperatorOptions options = {});
  MLOperand min(MLOperand a, MLOperand b, optional MLOperatorOptions options = {});
  MLOperand pow(MLOperand a, MLOperand b, optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLBinarySupportLimits add;
  MLBinarySupportLimits sub;
  MLBinarySupportLimits mul;
  MLBinarySupportLimits div;
  MLBinarySupportLimits max;
  MLBinarySupportLimits min;
  MLBinarySupportLimits pow;
};

partial interface MLGraphBuilder {
  MLOperand equal(MLOperand a,
                  MLOperand b,
                  optional MLOperatorOptions options = {});
  MLOperand notEqual(MLOperand a,
                     MLOperand b,
                     optional MLOperatorOptions options = {});
  MLOperand greater(MLOperand a,
                    MLOperand b,
                    optional MLOperatorOptions options = {});
  MLOperand greaterOrEqual(MLOperand a,
                           MLOperand b,
                           optional MLOperatorOptions options = {});
  MLOperand lesser(MLOperand a,
                   MLOperand b,
                   optional MLOperatorOptions options = {});
  MLOperand lesserOrEqual(MLOperand a,
                          MLOperand b,
                          optional MLOperatorOptions options = {});
  MLOperand logicalNot(MLOperand a, optional MLOperatorOptions options = {});
  MLOperand logicalAnd(MLOperand a,
                       MLOperand b,
                       optional MLOperatorOptions options = {});
  MLOperand logicalOr(MLOperand a,
                      MLOperand b,
                      optional MLOperatorOptions options = {});
  MLOperand logicalXor(MLOperand a,
                       MLOperand b,
                       optional MLOperatorOptions options = {});
  MLOperand isNaN(MLOperand a, optional MLOperatorOptions options = {});
  MLOperand isInfinite(MLOperand a, optional MLOperatorOptions options = {});
};

dictionary MLLogicalNotSupportLimits {
  MLTensorLimits a;
  MLTensorLimits output;
};

partial dictionary MLOpSupportLimits {
  MLBinarySupportLimits equal;
  MLBinarySupportLimits notEqual;
  MLBinarySupportLimits greater;
  MLBinarySupportLimits greaterOrEqual;
  MLBinarySupportLimits lesser;
  MLBinarySupportLimits lesserOrEqual;
  MLLogicalNotSupportLimits logicalNot;
  MLBinarySupportLimits logicalAnd;
  MLBinarySupportLimits logicalOr;
  MLBinarySupportLimits logicalXor;
  MLLogicalNotSupportLimits isNaN;
  MLLogicalNotSupportLimits isInfinite;
};

partial interface MLGraphBuilder {
  MLOperand abs(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand ceil(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand cos(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand erf(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand exp(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand floor(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand identity(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand log(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand neg(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand reciprocal(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand roundEven(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand sin(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand sign(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand sqrt(MLOperand input, optional MLOperatorOptions options = {});
  MLOperand tan(MLOperand input, optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits abs;
  MLSingleInputSupportLimits ceil;
  MLSingleInputSupportLimits cos;
  MLSingleInputSupportLimits erf;
  MLSingleInputSupportLimits exp;
  MLSingleInputSupportLimits floor;
  MLSingleInputSupportLimits identity;
  MLSingleInputSupportLimits log;
  MLSingleInputSupportLimits neg;
  MLSingleInputSupportLimits reciprocal;
  MLSingleInputSupportLimits roundEven;
  MLSingleInputSupportLimits sin;
  MLSingleInputSupportLimits sign;
  MLSingleInputSupportLimits sqrt;
  MLSingleInputSupportLimits tan;
};

partial interface MLGraphBuilder {
  MLOperand dequantizeLinear(MLOperand input,
                             MLOperand scale,
                             MLOperand zeroPoint,
                             optional MLOperatorOptions options = {});
};

dictionary MLQuantizeDequantizeLinearSupportLimits {
  MLTensorLimits input;
  MLTensorLimits scale;
  MLTensorLimits zeroPoint;
  MLTensorLimits output;
};

partial dictionary MLOpSupportLimits {
  MLQuantizeDequantizeLinearSupportLimits dequantizeLinear;
};

partial interface MLGraphBuilder {
  MLOperand quantizeLinear(MLOperand input,
                           MLOperand scale,
                           MLOperand zeroPoint,
                           optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLQuantizeDequantizeLinearSupportLimits quantizeLinear;
};

dictionary MLEluOptions : MLOperatorOptions {
  double alpha = 1;
};

partial interface MLGraphBuilder {
  MLOperand elu(MLOperand input, optional MLEluOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits elu;
};

partial interface MLGraphBuilder {
  MLOperand expand(MLOperand input,
                   sequence<[EnforceRange] unsigned long> newShape,
                   optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits expand;
};

dictionary MLGatherOptions : MLOperatorOptions {
  [EnforceRange] unsigned long axis = 0;
};

partial interface MLGraphBuilder {
  MLOperand gather(MLOperand input,
                   MLOperand indices,
                   optional MLGatherOptions options = {});
};

dictionary MLGatherSupportLimits {
  MLTensorLimits input;
  MLTensorLimits indices;
  MLTensorLimits output;
};

partial dictionary MLOpSupportLimits {
  MLGatherSupportLimits gather;
};

partial interface MLGraphBuilder {
  MLOperand gatherElements(MLOperand input,
                           MLOperand indices,
                           optional MLGatherOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLGatherSupportLimits gatherElements;
};

partial interface MLGraphBuilder {
  MLOperand gatherND(MLOperand input,
                     MLOperand indices,
                     optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLGatherSupportLimits gatherND;
};

partial interface MLGraphBuilder {
  MLOperand gelu(MLOperand input, optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits gelu;
};

dictionary MLGemmOptions : MLOperatorOptions {
  MLOperand c;
  double alpha = 1.0;
  double beta = 1.0;
  boolean aTranspose = false;
  boolean bTranspose = false;
};

partial interface MLGraphBuilder {
  MLOperand gemm(MLOperand a, MLOperand b, optional MLGemmOptions options = {});
};

dictionary MLGemmSupportLimits {
  MLTensorLimits a;
  MLTensorLimits b;
  MLTensorLimits c;
  MLTensorLimits output;
};

partial dictionary MLOpSupportLimits {
  MLGemmSupportLimits gemm;
};

enum MLGruWeightLayout {
  "zrn",  // update-reset-new gate ordering
  "rzn"   // reset-update-new gate ordering
};

enum MLRecurrentNetworkActivation {
  "relu",
  "sigmoid",
  "tanh"
};

enum MLRecurrentNetworkDirection {
  "forward",
  "backward",
  "both"
};

dictionary MLGruOptions : MLOperatorOptions {
  MLOperand bias;
  MLOperand recurrentBias;
  MLOperand initialHiddenState;
  boolean resetAfter = true;
  boolean returnSequence = false;
  MLRecurrentNetworkDirection direction = "forward";
  MLGruWeightLayout layout = "zrn";
  sequence<MLRecurrentNetworkActivation> activations;
};

partial interface MLGraphBuilder {
  sequence<MLOperand> gru(MLOperand input,
                          MLOperand weight,
                          MLOperand recurrentWeight,
                          [EnforceRange] unsigned long steps,
                          [EnforceRange] unsigned long hiddenSize,
                          optional MLGruOptions options = {});
};

dictionary MLGruSupportLimits {
  MLTensorLimits input;
  MLTensorLimits weight;
  MLTensorLimits recurrentWeight;
  MLTensorLimits bias;
  MLTensorLimits recurrentBias;
  MLTensorLimits initialHiddenState;
  MLTensorLimits output0;
  MLTensorLimits output1;
};

partial dictionary MLOpSupportLimits {
  MLGruSupportLimits gru;
};

dictionary MLGruCellOptions : MLOperatorOptions {
  MLOperand bias;
  MLOperand recurrentBias;
  boolean resetAfter = true;
  MLGruWeightLayout layout = "zrn";
  sequence<MLRecurrentNetworkActivation> activations;
};

partial interface MLGraphBuilder {
  MLOperand gruCell(MLOperand input,
                    MLOperand weight,
                    MLOperand recurrentWeight,
                    MLOperand hiddenState,
                    [EnforceRange] unsigned long hiddenSize,
                    optional MLGruCellOptions options = {});
};

dictionary MLGruCellSupportLimits {
  MLTensorLimits input;
  MLTensorLimits weight;
  MLTensorLimits recurrentWeight;
  MLTensorLimits hiddenState;
  MLTensorLimits bias;
  MLTensorLimits recurrentBias;
  MLTensorLimits output;
};

partial dictionary MLOpSupportLimits {
  MLGruCellSupportLimits gruCell;
};

dictionary MLHardSigmoidOptions : MLOperatorOptions {
  double alpha = 0.2;
  double beta = 0.5;
};

partial interface MLGraphBuilder {
  MLOperand hardSigmoid(MLOperand input, optional MLHardSigmoidOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits hardSigmoid;
};

partial interface MLGraphBuilder {
  MLOperand hardSwish(MLOperand input, optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits hardSwish;
};

dictionary MLInstanceNormalizationOptions : MLOperatorOptions {
  MLOperand scale;
  MLOperand bias;
  double epsilon = 1e-5;
  MLInputOperandLayout layout = "nchw";
};

partial interface MLGraphBuilder {
  MLOperand instanceNormalization(
    MLOperand input,
    optional MLInstanceNormalizationOptions options = {});
};

dictionary MLNormalizationSupportLimits {
  MLTensorLimits input;
  MLTensorLimits scale;
  MLTensorLimits bias;
  MLTensorLimits output;
};

partial dictionary MLOpSupportLimits {
  MLNormalizationSupportLimits instanceNormalization;
};

dictionary MLLayerNormalizationOptions : MLOperatorOptions {
  MLOperand scale;
  MLOperand bias;
  sequence<[EnforceRange] unsigned long> axes;
  double epsilon = 1e-5;
};

partial interface MLGraphBuilder {
  MLOperand layerNormalization(MLOperand input,
                               optional MLLayerNormalizationOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLNormalizationSupportLimits layerNormalization;
};

dictionary MLLeakyReluOptions : MLOperatorOptions {
  double alpha = 0.01;
};

partial interface MLGraphBuilder {
  MLOperand leakyRelu(MLOperand input, optional MLLeakyReluOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits leakyRelu;
};

dictionary MLLinearOptions : MLOperatorOptions {
  double alpha = 1;
  double beta = 0;
};

partial interface MLGraphBuilder {
  MLOperand linear(MLOperand input, optional MLLinearOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits linear;
};

enum MLLstmWeightLayout {
  "iofg", // input-output-forget-cell gate ordering
  "ifgo"  // input-forget-cell-output gate ordering
};

dictionary MLLstmOptions : MLOperatorOptions {
  MLOperand bias;
  MLOperand recurrentBias;
  MLOperand peepholeWeight;
  MLOperand initialHiddenState;
  MLOperand initialCellState;
  boolean returnSequence = false;
  MLRecurrentNetworkDirection direction = "forward";
  MLLstmWeightLayout layout = "iofg";
  sequence<MLRecurrentNetworkActivation> activations;
};

partial interface MLGraphBuilder {
  sequence<MLOperand> lstm(MLOperand input,
                           MLOperand weight,
                           MLOperand recurrentWeight,
                           [EnforceRange] unsigned long steps,
                           [EnforceRange] unsigned long hiddenSize,
                           optional MLLstmOptions options = {});
};

dictionary MLLstmSupportLimits {
  MLTensorLimits input;
  MLTensorLimits weight;
  MLTensorLimits recurrentWeight;
  MLTensorLimits bias;
  MLTensorLimits recurrentBias;
  MLTensorLimits peepholeWeight;
  MLTensorLimits initialHiddenState;
  MLTensorLimits initialCellState;
  MLTensorLimits output0;
  MLTensorLimits output1;
  MLTensorLimits output2;
};

partial dictionary MLOpSupportLimits {
  MLLstmSupportLimits lstm;
};


dictionary MLLstmCellOptions : MLOperatorOptions {
  MLOperand bias;
  MLOperand recurrentBias;
  MLOperand peepholeWeight;
  MLLstmWeightLayout layout = "iofg";
  sequence<MLRecurrentNetworkActivation> activations;
};

partial interface MLGraphBuilder {
  sequence<MLOperand> lstmCell(MLOperand input,
                               MLOperand weight,
                               MLOperand recurrentWeight,
                               MLOperand hiddenState,
                               MLOperand cellState,
                               [EnforceRange] unsigned long hiddenSize,
                               optional MLLstmCellOptions options = {});
};

dictionary MLLstmCellSupportLimits {
  MLTensorLimits input;
  MLTensorLimits weight;
  MLTensorLimits recurrentWeight;
  MLTensorLimits hiddenState;
  MLTensorLimits cellState;
  MLTensorLimits bias;
  MLTensorLimits recurrentBias;
  MLTensorLimits peepholeWeight;
  MLTensorLimits output0;
  MLTensorLimits output1;
};

partial dictionary MLOpSupportLimits {
  MLLstmCellSupportLimits lstmCell;
};

partial interface MLGraphBuilder {
  MLOperand matmul(MLOperand a, MLOperand b, optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLBinarySupportLimits matmul;
};

enum MLPaddingMode {
  "constant",
  "edge",
  "reflection"
};

dictionary MLPadOptions : MLOperatorOptions {
  MLPaddingMode mode = "constant";
  MLNumber value = 0;
};

partial interface MLGraphBuilder {
  MLOperand pad(MLOperand input,
                sequence<[EnforceRange] unsigned long> beginningPadding,
                sequence<[EnforceRange] unsigned long> endingPadding,
                optional MLPadOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits pad;
};

enum MLRoundingType {
  "floor",
  "ceil"
};

dictionary MLPool2dOptions : MLOperatorOptions {
  sequence<[EnforceRange] unsigned long> windowDimensions;
  sequence<[EnforceRange] unsigned long> padding;
  sequence<[EnforceRange] unsigned long> strides;
  sequence<[EnforceRange] unsigned long> dilations;
  MLInputOperandLayout layout = "nchw";
  MLRoundingType outputShapeRounding = "floor";
  sequence<[EnforceRange] unsigned long> outputSizes;
};

partial interface MLGraphBuilder {
  MLOperand averagePool2d(MLOperand input, optional MLPool2dOptions options = {});
  MLOperand l2Pool2d(MLOperand input, optional MLPool2dOptions options = {});
  MLOperand maxPool2d(MLOperand input, optional MLPool2dOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits averagePool2d;
  MLSingleInputSupportLimits l2Pool2d;
  MLSingleInputSupportLimits maxPool2d;
};

partial interface MLGraphBuilder {
  MLOperand prelu(MLOperand input,
                  MLOperand slope,
                  optional MLOperatorOptions options = {});
};

dictionary MLPreluSupportLimits {
  MLTensorLimits input;
  MLTensorLimits slope;
  MLTensorLimits output;
};

partial dictionary MLOpSupportLimits {
  MLPreluSupportLimits prelu;
};

dictionary MLReduceOptions : MLOperatorOptions {
  sequence<[EnforceRange] unsigned long> axes;
  boolean keepDimensions = false;
};

partial interface MLGraphBuilder {
  MLOperand reduceL1(MLOperand input, optional MLReduceOptions options = {});
  MLOperand reduceL2(MLOperand input, optional MLReduceOptions options = {});
  MLOperand reduceLogSum(MLOperand input, optional MLReduceOptions options = {});
  MLOperand reduceLogSumExp(MLOperand input, optional MLReduceOptions options = {});
  MLOperand reduceMax(MLOperand input, optional MLReduceOptions options = {});
  MLOperand reduceMean(MLOperand input, optional MLReduceOptions options = {});
  MLOperand reduceMin(MLOperand input, optional MLReduceOptions options = {});
  MLOperand reduceProduct(MLOperand input, optional MLReduceOptions options = {});
  MLOperand reduceSum(MLOperand input, optional MLReduceOptions options = {});
  MLOperand reduceSumSquare(MLOperand input, optional MLReduceOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits reduceL1;
  MLSingleInputSupportLimits reduceL2;
  MLSingleInputSupportLimits reduceLogSum;
  MLSingleInputSupportLimits reduceLogSumExp;
  MLSingleInputSupportLimits reduceMax;
  MLSingleInputSupportLimits reduceMean;
  MLSingleInputSupportLimits reduceMin;
  MLSingleInputSupportLimits reduceProduct;
  MLSingleInputSupportLimits reduceSum;
  MLSingleInputSupportLimits reduceSumSquare;
};

partial interface MLGraphBuilder {
  MLOperand relu(MLOperand input, optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits relu;
};

enum MLInterpolationMode {
  "nearest-neighbor",
  "linear"
};

dictionary MLResample2dOptions : MLOperatorOptions {
  MLInterpolationMode mode = "nearest-neighbor";
  sequence<float> scales;
  sequence<[EnforceRange] unsigned long> sizes;
  sequence<[EnforceRange] unsigned long> axes;
};

partial interface MLGraphBuilder {
  MLOperand resample2d(MLOperand input, optional MLResample2dOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits resample2d;
};

partial interface MLGraphBuilder {
  MLOperand reshape(MLOperand input,
                    sequence<[EnforceRange] unsigned long> newShape,
                    optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits reshape;
};

dictionary MLReverseOptions : MLOperatorOptions {
  sequence<[EnforceRange] unsigned long> axes;
};

partial interface MLGraphBuilder {
  MLOperand reverse(MLOperand input, optional MLReverseOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits reverse;
};

dictionary MLScatterOptions : MLOperatorOptions {
  [EnforceRange] unsigned long axis = 0;
};

partial interface MLGraphBuilder {
  MLOperand scatterElements(MLOperand input,
                            MLOperand indices,
                            MLOperand updates,
                            optional MLScatterOptions options = {});
};

dictionary MLScatterSupportLimits {
  MLTensorLimits input;
  MLTensorLimits indices;
  MLTensorLimits updates;
  MLTensorLimits output;
};

partial dictionary MLOpSupportLimits {
  MLScatterSupportLimits scatterElements;
};

partial interface MLGraphBuilder {
  MLOperand scatterND(MLOperand input,
                      MLOperand indices,
                      MLOperand updates,
                      optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLScatterSupportLimits scatterND;
};

partial interface MLGraphBuilder {
  MLOperand sigmoid(MLOperand input, optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits sigmoid;
};

dictionary MLSliceOptions : MLOperatorOptions {
  sequence<[EnforceRange] unsigned long> strides;
};

partial interface MLGraphBuilder {
  MLOperand slice(MLOperand input,
                  sequence<[EnforceRange] unsigned long> starts,
                  sequence<[EnforceRange] unsigned long> sizes,
                  optional MLSliceOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits slice;
};

partial interface MLGraphBuilder {
  MLOperand softmax(MLOperand input,
                    [EnforceRange] unsigned long axis,
                    optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits softmax;
};

partial interface MLGraphBuilder {
  MLOperand softplus(MLOperand input, optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits softplus;
};

partial interface MLGraphBuilder {
  MLOperand softsign(MLOperand input, optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits softsign;
};

dictionary MLSplitOptions : MLOperatorOptions {
  [EnforceRange] unsigned long axis = 0;
};

partial interface MLGraphBuilder {
  sequence<MLOperand> split(
      MLOperand input,
      ([EnforceRange] unsigned long or sequence<[EnforceRange] unsigned long>) splits,
      optional MLSplitOptions options = {});
};

dictionary MLSplitSupportLimits {
  MLTensorLimits input;
  MLTensorLimits outputs;
};

partial dictionary MLOpSupportLimits {
  MLSplitSupportLimits split;
};

partial interface MLGraphBuilder {
  MLOperand tanh(MLOperand input, optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits tanh;
};

partial interface MLGraphBuilder {
  MLOperand tile(MLOperand input,
                 sequence<unsigned long> repetitions,
                 optional MLOperatorOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits tile;
};

dictionary MLTransposeOptions : MLOperatorOptions {
  sequence<[EnforceRange] unsigned long> permutation;
};

partial interface MLGraphBuilder {
  MLOperand transpose(MLOperand input, optional MLTransposeOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits transpose;
};

dictionary MLTriangularOptions : MLOperatorOptions {
  boolean upper = true;
  [EnforceRange] long diagonal = 0;
};

partial interface MLGraphBuilder {
  MLOperand triangular(MLOperand input, optional MLTriangularOptions options = {});
};

partial dictionary MLOpSupportLimits {
  MLSingleInputSupportLimits triangular;
};

partial interface MLGraphBuilder {
  MLOperand where(MLOperand condition,
                  MLOperand trueValue,
                  MLOperand falseValue,
                  optional MLOperatorOptions options = {});
};

dictionary MLWhereSupportLimits {
  MLTensorLimits condition;
  MLTensorLimits trueValue;
  MLTensorLimits falseValue;
  MLTensorLimits output;
};

partial dictionary MLOpSupportLimits {
  MLWhereSupportLimits where;
};

課題索引

範囲外アクセスの影響を受けやすい演算を、実装者への指針として文書化する。
rendererを実行しているプロセス間でCPUが共有されている現在の状態を考慮し、 side channel attackの実現可能性を調査する。
hintingは懸念を部分的に軽減する。追加の軽減策を調査する。
MLGraph.devices API extensionは、graphが完全に構築およびコンパイルされた後に 実行用に実際に選択されたdevicesを公開するために提案されている。このAPI extensionのprivacy implicationsは調査中である。 [Issue #836]
dispatch()中のerrorsを報告するためのmechanismの追加を検討する。 [Issue #778]
このtimelineをより厳密に定義する。 [Issue #529]
graph execution中のerrorsを報告するためのmechanismを追加する。 [Issue #778]
tensorへの書き込み中のerrorsを報告するためのmechanismを追加する。 [Issue #778]
0-size dimensionsはサポートされるべきか? [Issue #391]
operand dimensionsの最大数は定義されていないが、native ML APIsには通常、 サポートされる最大sizeがある。 [Issue #456]
各operatorについてサポートされなければならないdata typesのsubsetを指定すべきか?
bigintnumeric typesのunionsのサポートは [WEBIDL]では新しく、 implementation supportも限定的である。Prototype implementationsには、このapproachについてfeedbackを提供することが推奨される。 [whatwg/webidl Issue #1388]
0-size dimensionsが許可される場合、これらの手順を改訂する。 [Issue #391]
0-size dimensionsが許可される場合、上記の手順を改訂する。 [Issue #391]
0-size dimensionsが許可される場合、これらの手順を改訂する。 [Issue #391]
[INFRA]で定義が利用可能になったら、これを削除する。 [whatwg/infra Issue #664]