avatarBytefer

Free AI web copilot to create summaries, insights and extended knowledge, download it at here

4325

Abstract

<p id="4b15">In TypeScript, <code>any</code> type is called the top type. The so-called top type can be understood as a generic parent type, that is, a type that can contain all values.</p><figure id="00e8"><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/1*7EcOS41UYWEYCjnWiOzLKg.jpeg"><figcaption></figcaption></figure><p id="e4ee">In fact, any type is essentially an escape hatch for the type system, and <b>TypeScript allows us to perform any operation on the value of any type without performing any kind of prior checking</b>.</p><figure id="b7ac"><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/1*ln_2Py-2XJlh0E1eK6CW4g.jpeg"><figcaption></figcaption></figure><p id="f18a">What’s the problem with this? Let’s take an example:</p><figure id="7311"><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/1*mynXeUYaUUQ5URy7iWsCYQ.jpeg"><figcaption></figcaption></figure><p id="e85d">For the above TypeScript code, no errors will be prompted at compile time, but runtime errors will be thrown at runtime. As developers, <code>any</code> type gives us a lot of freedom, but it also brings some pitfalls. In order to solve the security risks of <code>any</code> type, the TypeScript team introduced the <code>unknown</code> type in 3.0, which you can understand as a type-safe <code>any</code> type.</p><p id="175d">I won’t go into the difference between <code>any</code> type and <code>unknown</code> type, but you can read the following article if you are interested.</p><div id="dd3e" class="link-block"> <a href="https://javascript.plainenglish.io/no-more-confusion-about-typescripts-any-and-unknown-98c4b53f8924"> <div> <div> <h2>No More Confusion About TypeScript’s ‘any’ and ‘unknown’</h2> <div><h3>Master the similarities and differences between any &amp; unknown types and avoid learning TypeScript as AnyScript.</h3></div> <div><p>javascript.plainenglish.io</p></div> </div> <div> <div style="background-image: url(https://miro.readmedium.com/v2/resize:fit:320/1*evY9FgxDDYbPGcOm79ELEQ.jpeg)"></div> </div> </div> </a> </div><p id="e2c5">Finally, let’s look at the complete code:</p><div id="69f4"><pre><span class="hljs-keyword">type</span> <span class="hljs-title class_">IsAny</span><span class="hljs-operator">&lt;</span>T<span class="hljs-operator">&gt;</span> <span class="hljs-operator">=</span> <span class="hljs-number">0</span> extends T <span class="hljs-operator">&amp;</span> <span class="hljs-number">1</span> <span class="hljs-operator">?</span> <span class="hljs-literal">true</span> <span class="hljs-operator">:</span> <span class="hljs-literal">false</span></pre></div><div id="445e"><pre><span class="hljs-keyword">type</span> <span class="hljs-type">A </span>= IsAny&lt;any&gt; // <span class="hljs-literal">true</span> <span class="hljs-keyword">type</span> <span class="hljs-type">B </span>= IsAny&lt;undefined&gt; // <span class="hljs-literal">false</span> <span class="hljs-keyword">type</span> <span class="hljs-type">C </span>= IsAny&lt;unknown&gt; // <span class="hljs-literal">false</span> <span class="hljs-keyword">type</span> <span class="hljs-type">D </span>= IsAny&lt;never&gt; // <span class="hljs-literal">false</span> <span class="hljs-keyword">type</span> <span class="hljs-type">E </span>= IsAny&lt;string&gt; // <span class="hljs-literal">false</span></pre></div><p id="d8d7">In TypeScript, the <code>&amp;</code> operator is provided for us to implement the intersection operation on multiple types, and the resulting new type is called the intersection type.</p><p id="10f4">Let’s briefly introduce the <code>&amp;</code> operator, which satisfies the following rules:</p><ul><li>Identity: <code>A &amp; A</code> is equivalent to <code>A</code>.</li><li>Commutativity: <code>A &amp; B</code> is equivalent to <code>B &amp; A</code> (except for call and construct signatures as noted below).</li><li>Associativity: <code>(A &amp; B) &amp; C</code> is equivalent to <code>A &amp; (B &amp; C)</code>.</li><li>Supertype collapsing: <code>A &amp; B</code> is equivalent to <code>A</code> if <code>B</code> is a supertype of <code>A</code>.</li></ul><figure id="cb57 # Options "><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/1*GZiZDsFEd45fyqeqzF52zQ.jpeg"><figcaption></figcaption></figure><p id="79c3">In the above code, <code>any</code> type and <code>never</code> type are special. Except for the <code>never</code> type, other type intersecting with <code>any</code> type will result in <code>any</code> type.</p><p id="9055">After understanding the characteristics of the <code>any</code> type, let’s take a look at the output of <code>T &amp; 1</code> when the <code>T</code> type parameter is of a different type:</p><div id="0a46"><pre><span class="hljs-keyword">type</span> <span class="hljs-variable constant_">A1</span> = <span class="hljs-built_in">any</span> &amp; <span class="hljs-number">1</span> <span class="hljs-comment">// any</span> <span class="hljs-keyword">type</span> <span class="hljs-variable constant_">B1</span> = <span class="hljs-literal">undefined</span> &amp; <span class="hljs-number">1</span> <span class="hljs-comment">// never</span> <span class="hljs-keyword">type</span> <span class="hljs-variable constant_">C1</span> = <span class="hljs-built_in">unknown</span> &amp; <span class="hljs-number">1</span> <span class="hljs-comment">// 1</span> <span class="hljs-keyword">type</span> <span class="hljs-variable constant_">D1</span> = <span class="hljs-built_in">never</span> &amp; <span class="hljs-number">1</span> <span class="hljs-comment">// never</span> <span class="hljs-keyword">type</span> <span class="hljs-variable constant_">E1</span> = <span class="hljs-built_in">string</span> &amp; <span class="hljs-number">1</span> <span class="hljs-comment">// never</span></pre></div><p id="0a59">After mastering the above content, the rest is the related content of TypeScript <b>conditional types</b>, which will not be introduced here. I recommend you to read this article:</p><div id="e3c7" class="link-block"> <a href="https://javascript.plainenglish.io/use-typescript-conditional-types-like-a-pro-7baea0ad05c5"> <div> <div> <h2>Using TypeScript Conditional Types Like a Pro</h2> <div><h3>Explained with animations. Master TypeScript Conditional Types and understand how TypeScript’s built-in Utility Types…</h3></div> <div><p>javascript.plainenglish.io</p></div> </div> <div> <div style="background-image: url(https://miro.readmedium.com/v2/resize:fit:320/1*aLZcvGGCMruzNeYCHbHtDQ.jpeg)"></div> </div> </div> </a> </div><p id="61b9">If there is anything unclear, please leave me a message. You also can follow me on <a href="https://medium.com/@bytefer">Medium</a> or <a href="https://twitter.com/Tbytefer">Twitter</a> to read more about TypeScript and JavaScript!</p><h1 id="e9dd">Resources</h1><div id="cd9c" class="link-block"> <a href="https://github.com/type-challenges/type-challenges/blob/main/questions/00223-hard-isany/README.md"> <div> <div> <h2>type-challenges/README.md at main · type-challenges/type-challenges</h2> <div><h3>by Pavel Glushkov @pashutk Sometimes it's useful to detect if you have a value with any type. This is especially…</h3></div> <div><p>github.com</p></div> </div> <div> <div style="background-image: url(https://miro.readmedium.com/v2/resize:fit:320/0*PfhnNiVinJlX6V4O)"></div> </div> </div> </a> </div><div id="4ee5" class="link-block"> <a href="https://readmedium.com/with-these-articles-you-will-not-be-confused-when-learning-typescript-d96a5c99e229"> <div> <div> <h2>With 30+ Articles, You Will Not Be Confused When Learning TypeScript</h2> <div><h3>Through Vivid Animations, You Can Easily Understand the Difficult Points and Core Knowledge of TypeScript! Continuously…</h3></div> <div><p>medium.com</p></div> </div> <div> <div style="background-image: url(https://miro.readmedium.com/v2/resize:fit:320/1*f1j_y98p4zYxXGLD-fNvDQ.jpeg)"></div> </div> </div> </a> </div></article></body>

Type Challenges: Implement the IsAny<T> Utility Type

99% of TypeScript Developers Have Used the Any Type. But Only 20% of Developers Know How To Detect Any Type.

Welcome to the Mastering TypeScript series, there are dozens of articles in this series. To help readers better consolidate their knowledge of TypeScript, I have selected a few dozen challenges from the type-challenges repository on Github to complete the type challenge with you.

Challenge

Sometimes it’s useful to detect if you have a value with any type. This is especially helpful while working with third-party TypeScript modules, which can export any values in the module API. It's also good to know about any when you're suppressing implicitAny checks.

So, let’s write a utility type IsAny<T>, which takes input type T. If T is any, return true, otherwise, return false.

For example:

type A = IsAny<any> // expected to be true
type B = IsAny<undefined> // expected to be false
type C = IsAny<unknown> // expected to be false
type D = IsAny<never> // expected to be false
type E = IsAny<string> // expected to be false

Solution

Our type challenge is to implement the IsAny<T> generic, before we analyze how to implement this generic type, let’s briefly introduce the any type.

Any Type

In TypeScript, any type is called the top type. The so-called top type can be understood as a generic parent type, that is, a type that can contain all values.

In fact, any type is essentially an escape hatch for the type system, and TypeScript allows us to perform any operation on the value of any type without performing any kind of prior checking.

What’s the problem with this? Let’s take an example:

For the above TypeScript code, no errors will be prompted at compile time, but runtime errors will be thrown at runtime. As developers, any type gives us a lot of freedom, but it also brings some pitfalls. In order to solve the security risks of any type, the TypeScript team introduced the unknown type in 3.0, which you can understand as a type-safe any type.

I won’t go into the difference between any type and unknown type, but you can read the following article if you are interested.

Finally, let’s look at the complete code:

type IsAny<T> = 0 extends T & 1 ? true : false
type A = IsAny<any> // true
type B = IsAny<undefined> // false
type C = IsAny<unknown> // false
type D = IsAny<never> // false
type E = IsAny<string> // false

In TypeScript, the & operator is provided for us to implement the intersection operation on multiple types, and the resulting new type is called the intersection type.

Let’s briefly introduce the & operator, which satisfies the following rules:

  • Identity: A & A is equivalent to A.
  • Commutativity: A & B is equivalent to B & A (except for call and construct signatures as noted below).
  • Associativity: (A & B) & C is equivalent to A & (B & C).
  • Supertype collapsing: A & B is equivalent to A if B is a supertype of A.

In the above code, any type and never type are special. Except for the never type, other type intersecting with any type will result in any type.

After understanding the characteristics of the any type, let’s take a look at the output of T & 1 when the T type parameter is of a different type:

type A1 = any & 1 // any
type B1 = undefined & 1 // never
type C1 = unknown & 1 // 1
type D1 = never & 1 // never
type E1 = string & 1 // never

After mastering the above content, the rest is the related content of TypeScript conditional types, which will not be introduced here. I recommend you to read this article:

If there is anything unclear, please leave me a message. You also can follow me on Medium or Twitter to read more about TypeScript and JavaScript!

Resources

Typescript
JavaScript
Front End Development
Web Development
Programming
Recommended from ReadMedium