web-dev-qa-db-ja.com

関数型プログラミングの擁護者は、ReactまたはAngularなどのフレームワークをどのように使用しますか?

私は最近このブログ投稿を読みました: JavaScriptの2つの柱パート1:地獄​​の7番目の円をエスケープする方法 、本質的にオブジェクト指向プログラミングに対する批判であり、代わりに関数型プログラミングの擁護です。

作成されたいくつかの重要なポイント:

  • コンストラクターは、すべての呼び出し元をオブジェクトのインスタンス化方法の詳細に結び付けるため、オープン/クローズの原則に違反しています。 ... JavaScriptはコンストラクター関数を必要としません。これは、どの関数でも新しいオブジェクトを返すことができるためです。動的オブジェクト拡張、オブジェクトリテラル、およびObject.create()を使用すると、必要なものはすべて揃っています。そして、thisは他の関数と同じように動作します。ばんざーい!

  • 古典的な継承では、一般的に単一の祖先からのみ継承できるため、厄介な分類法を強制されます。間違いなく、大規模なアプリケーションで見たすべてのOOデザイン分類法が最終的に間違っていたので、ぎこちないと言います。

  • 子クラスとその親の間の結合は、OO設計における結合の最も緊密な形式です。これは、再利用可能なモジュール式コードの反対です。

    クラスに小さな変更を加えると、完全に無関係であるはずのものを壊す波打つような副作用が生じます。

わかりました。これらの引数のメリットを議論せずに(この記事はいくつかのコード例で可能だと思います)-この機能/プロトタイプのハッキングパラダイムは実際にどのように使用されていますか?

すなわち。特にAngularまたはReact-のようなフレームワークに関しては、コンポーネントの基盤はフレームワークの親クラスを拡張するES6クラスです。

2
dwjohnston

以前の役割では、Reactでほとんど純粋な関数を使用していました。 Reactは「ユーザーインターフェースを構築するためのライブラリ」です。Reactコンポーネントが非常にオブジェクト指向であり、状態、動作、UIをカプセル化しているプロジェクトがよく見られます、そしてスタイルです。トレードオフがあります。これらすべてのものをコンポーネントにカプセル化すると、間違いなく読みやすさが向上しますが、柔軟性、再利用性、テスト容易性、疎結合が失われます。

まず、Reactコンポーネントからすべての動作を分離し、コンポーネントプロパティを介して動作を注入することをお勧めします。その後、すべての動作を純粋な関数として定義することもできます-ステートフルな動作も含めます。チェックしてください- Recompose高次コンポーネント の束の場合は、コンポーネントの状態を処理するときに機能を維持するのに役立ちます Redux はアプリケーションの状態の場合。

具体的な例として、カウンターをインクリメントするボタンを考えてみましょう。オブジェクト指向コンポーネントを使用すると、次のように記述できます。

class Counter extends React.Component {
  constructor(props) {
    super(props)
    this.state = {
      counter: 0,
    }
  }

  render() {
    const {
      counter,
    } = this.state

    const onClick = () => {
      this.setState({
        counter: counter + 1,
      })
    }

    return (
      <button onClick={onClick}>Val {counter} click to increase</button>
    )
  }
}

関数型プログラミングでは、次のように記述します。

// pure functional component
const Counter = ({
  onClick,
  counter,
}) => (
  <button onClick={onClick}>Val {counter} click to increase</button>
)


// elsewhere define the behavior again as pure functions
const FunctionalCounter = Recompose.withStateHandlers({
  counter: 0, // our initial state
}, {
  onClick: ({ counter }) => () => ({ // a pure function that takes state, props, and parameters and updates state
    counter: counter + 1,
  }),
})(Counter)

AngularはUIライブラリではなく、「フロントエンドWebアプリケーションフレームワーク」であり、アプリケーションの記述方法に多くの制約を課すため、まったく別の獣です。 Angularアプリケーションを関数型プログラミングで作成する方法に慣れていませんが、Reactで行ったのと同じ原則を適用できます。具体的には、動作とビジネスロジックをUIは、UIに注入される慎重に整理された関数に組み込まれます(つまり、Angularの依存性注入を使用してビジネスロジック関数を挿入できます)。通常、アプリケーションロジックがUIフレームワークに結合されないように、これを行うことをお勧めします。

3
Samuel