Typescript 非虚假类型,也称为真实类型

Typescript 非虚假类型,也称为真实类型,typescript,tsc,Typescript,Tsc,在TypeScript中,有truthy的类型吗 我有这个方法: 对象。钥匙(lck。锁夹)。长度; 排队(k:any,obj?:any):无效 顺便说一下,使用TS可以检查空字符串“”。 我想把它转换成: enqueue(k: Truthy, obj?: any): void 除了我不知道如何定义Truthy的类型。顺便说一句,我认为使用TS可以检查空字符串“” 我之所以要这样做,是因为我不希望用户传入null,未定义的,',等等,作为散列的键。我不知道为什么需要它,但这很有趣。老实说,

在TypeScript中,有truthy的类型吗

我有这个方法: 对象。钥匙(lck。锁夹)。长度; 排队(k:any,obj?:any):无效 顺便说一下,使用TS可以检查空字符串“”。 我想把它转换成:

  enqueue(k: Truthy, obj?: any): void
除了我不知道如何定义Truthy的类型。顺便说一句,我认为使用TS可以检查空字符串“”


我之所以要这样做,是因为我不希望用户传入
null
未定义的
'
,等等,作为散列的键。

我不知道为什么需要它,但这很有趣。老实说,简短的回答是:TypeScript不适合这种情况,您最好进行运行时检查并记录代码,以便开发人员知道
k
参数应该是真实的。不过,如果您打算强制TypeScript执行类似操作,请继续阅读:


注意:要使下面的代码正常工作,请启用
stricnullchecks
编译器选项。这有点必要,因为无法区分
Truthy
Truthy | null | undefined
将是一个问题

你几乎可以定义,就像

type Falsy = false | 0 | "" | null | undefined 
除了
NaN
也是falsy之外,TypeScript是
NaN
的数字文本

即使您有如上所述的
Falsy
,也没有in-TypeScript,因此无法将
Truthy
表示为“除了
Falsy
之外的所有内容”

您可以尝试使用use排除
enqueue()
中可能存在的错误参数,但这很奇怪:

type DefinitelyTruthy<T> =
  false extends T ? never :
  0 extends T ? never :
  "" extends T ? never :
  null extends T ? never :
  undefined extends T ? never :
  T

declare function enqueue<T extends number | string | true | object>(
  k: T & DefinitelyTruthy<T>,
  obj?: any
): void

declare const str: string;
enqueue(str); // error, might be falsy
enqueue("a"); // okay
enqueue(1); // okay
enqueue(0); // error
enqueue(NaN); // error
enqueue(true); // okay
enqueue(false); // error
enqueue([]); //okay
enqueue({a: "hello"}); // okay
enqueue({}); // error, interpreted as type {} which could be an empty string:
const zilch = "" as {};
enqueue(zilch); // error, see? 

所有这些都很好,但不幸的是,如果您将常规
字符串
传递给
enqueue()
将失败,有时开发人员可能需要这样做,如果他们用于
k
参数的值不是他们指定的字符串文字:

declare const str: string; // comes from somewhere else
enqueue(str); // error!  how do I do this?
要解决此问题,您可以尝试创建一个可用于向编译器标识已检查值是否为空的字符串,然后创建一个用于将
字符串
约束为该类型的:

type NotEmptyString = string & {"***NotEmptyString***": true};
function notEmptyString(x: string): x is NotEmptyString {
  return x !== "";
}
现在,开发人员可以执行以下操作:

declare const str: string;
enqueue(str); // error, might be falsy
if (notEmptyString(str)) {
  enqueue(str); // okay, str is NotEmptyString
}


唷!这是一个很大的篮球跳跃。这取决于你是否认为这是值得的。好的,希望能有帮助。祝你好运

没有
Truthy
type,但是你可以利用type-guard-system()来帮助TypeScript理解真正的
Truthy
并分配它
Truthy
type

让我们定义
Falsy
类型和
istruty
函数:

type Falsy = false | 0 | '' | null | undefined;

// this is a type predicate - if x is `truthy`, then it's T
const isTruthy = <T>(x: T | Falsy): x is T => !!x;

{   // removing boolean "false" type
  const result: string | false = Math.random() > 0.5 ? 'a' : false;
  const truthyResult: string = isTruthy(result) ? result : 'was false';
}
{   // filtering only numbers from array
  const result: (number | undefined)[] = [42, undefined, 8, 16];
  const truthyResult: number[] = result.filter(isTruthy);
}
{   // filtering only Promises from array
  const result: (Promise<string> | null)[] = [Promise.resolve('a'), null, Promise.resolve('b'), Promise.resolve('c')];
  const truthyResult: Promise<string>[] = result.filter(isTruthy);
}


请注意,
string
不能转换为这样的类型(因为
'
是虚假的,但却是
字符串
),限制了它的用途。这似乎是您希望在运行时检查的内容。一个真实的类型感觉有点超出了TSI的范围,我试过这个,但它的错误的一切。例如,
enqueue(“a”)
给出了类型为“a”的错误
参数不可分配给类型为“never”的参数。
打开
--strictNullChecks
。。。如果你想区分
未定义的
/
空的
和真实的东西,你可能无论如何都需要它。请注意。0是一个数字(即使是假的)。因此,第二个示例实际上会从数组中过滤出0,如果它存在于数组中的话。
{   // removing boolean "false" type
  const result: string | false = Math.random() > 0.5 ? 'a' : false;
  const truthyResult: string = isTruthy(result) ? result : 'was false';
}
{   // filtering only numbers from array
  const result: (number | undefined)[] = [42, undefined, 8, 16];
  const truthyResult: number[] = result.filter(isTruthy);
}
{   // filtering only Promises from array
  const result: (Promise<string> | null)[] = [Promise.resolve('a'), null, Promise.resolve('b'), Promise.resolve('c')];
  const truthyResult: Promise<string>[] = result.filter(isTruthy);
}