


Confusing behavior of TypeScript type inference: Why do the four function return value types have the same result, and the trap of union types in conditional types?
Singular behavior of TypeScript type inference: Four functions return the same result defined by the value type and the trap of joint types in the conditional type
This article analyzes some puzzling type inference behavior in TypeScript. We will explore why four seemingly different type definitions yield the same results and explain the problems that may be encountered when using union types in conditional types.
First, let's observe these four getReturnType
type definitions:
type getReturnType1<t> = T extends (...args: never) => infer R ? R : never; type getReturnType2<t> = T extends (...args: never[]) => infer R ? R : never; type getReturnType3<t> = T extends (...args: any[]) => infer R ? R : never; type getReturnType4<t> = T extends (...args: any) => infer R ? R : never;</t></t></t></t>
Although ...args
are never
, never[]
, any[]
and any
, these four definitions produce the same results in practical applications. This is because in TypeScript's type system, the role of function parameter types in type inference is not what we intuitively think. never
represents a value that never exists, never[]
represents an empty array, any[]
represents an arbitrary type array, any
represents any type. However, extends
condition judgment mainly focuses on the return value type of the function infer R
, and the impact of the parameter type is relatively small and can even be ignored. Therefore, as long as the passed T
is a function type, the return value type can be inferred and assigned to R
; if T
is not a function type, it will return never
.
Next, we analyze another question, involving conditional types and union types:
type Props<t extends major rescategorylabel> = { labels: T[]; setSelect: (index: number, label: T extends Major ? Major : ResCategoryLabel) => void; xxx; }; const changeSelect = ( index: number, label: Major | ResCategoryLabel, e: React.MouseEvent<htmlanchorelement> | React.TouchEvent<htmlanchorelement> ) => { setSelect(index, label); // Type error activeTabToCenter(e.currentTarget as HTMLElement); };</htmlanchorelement></htmlanchorelement></t>
In this code, the Props
type defines a generic T
that limits it to a joint type of Major
or ResCategoryLabel
. The second parameter label
of setSelect
function is defined as T extends Major ? Major : ResCategoryLabel
. The original intention is to determine the type of label
based on the type of T
: if T
is Major
, then label
is Major
; otherwise it is ResCategoryLabel
. However, since T
is a union type, TypeScript cannot determine the specific type of T
at compile time, resulting in the type check of setSelect
function failing. This is because when the conditional type processes union types, each type will be judged separately, and the final result is a union of all branch results. In this case, the type of label
will eventually become Major | ResCategoryLabel
, which does not match the type of label
in the changeSelect
function, resulting in a type error. Workarounds may require redesigning the type definition, such as using type guards or finer type inference to avoid this problem.
The above is the detailed content of Confusing behavior of TypeScript type inference: Why do the four function return value types have the same result, and the trap of union types in conditional types?. For more information, please follow other related articles on the PHP Chinese website!

Hot AI Tools

Undresser.AI Undress
AI-powered app for creating realistic nude photos

AI Clothes Remover
Online AI tool for removing clothes from photos.

Undress AI Tool
Undress images for free

Clothoff.io
AI clothes remover

Video Face Swap
Swap faces in any video effortlessly with our completely free AI face swap tool!

Hot Article

Hot Tools

Notepad++7.3.1
Easy-to-use and free code editor

SublimeText3 Chinese version
Chinese version, very easy to use

Zend Studio 13.0.1
Powerful PHP integrated development environment

Dreamweaver CS6
Visual web development tools

SublimeText3 Mac version
God-level code editing software (SublimeText3)

Hot Topics

Troubleshooting and solutions to the company's security software that causes some applications to not function properly. Many companies will deploy security software in order to ensure internal network security. ...

The following steps can be used to resolve the problem that Navicat cannot connect to the database: Check the server connection, make sure the server is running, address and port correctly, and the firewall allows connections. Verify the login information and confirm that the user name, password and permissions are correct. Check network connections and troubleshoot network problems such as router or firewall failures. Disable SSL connections, which may not be supported by some servers. Check the database version to make sure the Navicat version is compatible with the target database. Adjust the connection timeout, and for remote or slower connections, increase the connection timeout timeout. Other workarounds, if the above steps are not working, you can try restarting the software, using a different connection driver, or consulting the database administrator or official Navicat support.

Common problems and solutions for Hadoop Distributed File System (HDFS) configuration under CentOS When building a HadoopHDFS cluster on CentOS, some common misconfigurations may lead to performance degradation, data loss and even the cluster cannot start. This article summarizes these common problems and their solutions to help you avoid these pitfalls and ensure the stability and efficient operation of your HDFS cluster. Rack-aware configuration error: Problem: Rack-aware information is not configured correctly, resulting in uneven distribution of data block replicas and increasing network load. Solution: Double check the rack-aware configuration in the hdfs-site.xml file and use hdfsdfsadmin-printTopo

Redis memory soaring includes: too large data volume, improper data structure selection, configuration problems (such as maxmemory settings too small), and memory leaks. Solutions include: deletion of expired data, use compression technology, selecting appropriate structures, adjusting configuration parameters, checking for memory leaks in the code, and regularly monitoring memory usage.

VS Code can run on Windows 8, but the experience may not be great. First make sure the system has been updated to the latest patch, then download the VS Code installation package that matches the system architecture and install it as prompted. After installation, be aware that some extensions may be incompatible with Windows 8 and need to look for alternative extensions or use newer Windows systems in a virtual machine. Install the necessary extensions to check whether they work properly. Although VS Code is feasible on Windows 8, it is recommended to upgrade to a newer Windows system for a better development experience and security.

VS Code can be used to write Python and provides many features that make it an ideal tool for developing Python applications. It allows users to: install Python extensions to get functions such as code completion, syntax highlighting, and debugging. Use the debugger to track code step by step, find and fix errors. Integrate Git for version control. Use code formatting tools to maintain code consistency. Use the Linting tool to spot potential problems ahead of time.

Common reasons why Navicat cannot connect to the database and its solutions: 1. Check the server's running status; 2. Check the connection information; 3. Adjust the firewall settings; 4. Configure remote access; 5. Troubleshoot network problems; 6. Check permissions; 7. Ensure version compatibility; 8. Troubleshoot other possibilities.

Redis memory fragmentation refers to the existence of small free areas in the allocated memory that cannot be reassigned. Coping strategies include: Restart Redis: completely clear the memory, but interrupt service. Optimize data structures: Use a structure that is more suitable for Redis to reduce the number of memory allocations and releases. Adjust configuration parameters: Use the policy to eliminate the least recently used key-value pairs. Use persistence mechanism: Back up data regularly and restart Redis to clean up fragments. Monitor memory usage: Discover problems in a timely manner and take measures.
