【问题标题】:What is an fp-ts Predicate?什么是 fp-ts 谓词?
【发布时间】:2021-08-01 11:41:39
【问题描述】:

我正在尝试使用 fp-ts 实现一些简单的数据验证,并遇到了这个codesandboxexample

import * as E from "fp-ts/lib/Either";
import { getSemigroup, NonEmptyArray } from "fp-ts/lib/NonEmptyArray";
import { sequence } from "fp-ts/lib/Array";
import { pipe } from "fp-ts/lib/pipeable";
import { Predicate } from "fp-ts/lib/function";

type ValidationError = NonEmptyArray<string>;

type ValidationResult = E.Either<ValidationError, unknown>;

type ValidationsResult<T> = E.Either<ValidationError, T>;

interface Validator {
  (x: unknown): ValidationResult;
}

interface Name extends String {}

const applicativeV = E.getValidation(getSemigroup<string>());

const validateName: (
  validations: Array<Validator>,
  value: unknown
) => ValidationsResult<Name> = (validations, value) =>
  validations.length
    ? pipe(
        sequence(applicativeV)(validations.map((afb) => afb(value))),
        E.map(() => value as Name)
      )
    : E.right(value as Name);

const stringLengthPredicate: Predicate<unknown> = (v) =>
  typeof v === "string" && v.length > 4;

const lengthAtLeastFour: Validator = E.fromPredicate(
  stringLengthPredicate,
  () => ["value must be a string of at least 5 characters"]
);

const requiredLetterPredicate: Predicate<unknown> = (v) =>
  typeof v === "string" && v.includes("t");

const hasLetterT: Validator = E.fromPredicate(requiredLetterPredicate, () => [
  'value must be a string that includes the letter "t"'
]);

const validations = [hasLetterT, lengthAtLeastFour];

console.log(validateName(validations, "sim"));
// {left: ['value must be a string that includes the letter "t"', 'value must be a string of at least 4 characters']}

console.log(validateName(validations, "timmy"));
// {right: 'timmy'}

Predicate 是什么?在这个例子中使用它有什么作用?我在文档中没有看到任何关于它的作用的解释,只是它是 part of the API 并且它似乎修改了提供的接口。

【问题讨论】:

  • 在编程中,谓词只是一个函数,它接受一个项目并返回一个布尔值。它通常用于条件逻辑,例如过滤arr.filter(somePredicate)。在您的情况下,它用于验证。似乎它需要一个项目,如果项目有效则返回true,否则返回false
  • Predicate&lt;A&gt; 是一个函数,它接受类型 A 的参数并返回一个布尔值(文档根据调用签名指定它:typescriptlang.org/docs/handbook/2/…)。它是验证框架中一个有用的构建块——谓词返回的布尔值可以解释为“参数是否有效”

标签: typescript fp-ts


【解决方案1】:

Predicate&lt;A&gt; = (a:A) =&gt; boolean

谓词是一个接受参数并返回布尔值的函数。它是 filterfromPredicate 采用的类型,属于 Option 和 Either 等许多类型。

例如,

import { filter } from 'fp-ts/Array'
import { pipe } from 'fp-ts/function'
import { fromPredicate } from 'fp-ts/Either'

const errorIfNotThree = fromPredicate<number>(x => x===3, () => 'not three!')
const f = pipe([1,2,3], filter(x => x===3))

errorIfNotThree(3) // right(3)
errorIfNotThree(5) // left('not three!')
f // [3]

在上面,x =&gt; x===3 的类型是 Predicate&lt;number&gt;,因为它是一个接受数字并返回布尔值的函数

【讨论】:

  • Predicate&lt;A&gt; = &lt;A&gt;(a:A) =&gt; boolean - 这是一个错误,因为第二个 &lt;A&gt; 创建了另一个隐藏第一个的类型变量,这实际上意味着该函数可以接受任何类型的参数,因为第二个 A 是与第一个无关(可以是调用者指定的任何类型)。应该是Predicate&lt;A&gt; = (a:A) =&gt; boolean
猜你喜欢
  • 1970-01-01
  • 2015-01-10
  • 1970-01-01
  • 1970-01-01
  • 2011-08-20
  • 2010-12-15
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多