Fact-checked by Grok 2 weeks ago

Union type

In , a is a that represents the union of two or more types, allowing a value to belong to any one of those types at a time, often interpreted set-theoretically as the set of all values from the constituent types. This concept enables variables or expressions to flexibly accommodate multiple possible data representations, contrasting with product types like or structs that combine multiple values simultaneously. Practical implementations of union types first appeared in programming languages in the 1970s, such as variant records in Pascal and untagged unions in . In practice, they manifest in two primary forms: untagged unions, which overlap for different types to optimize storage, and tagged unions (also known as sum types or variants), which include a discriminator to ensure at runtime or . Untagged unions, as in , allocate space equal to the largest member and allow only one member to be active, making them useful for -efficient type punning but prone to if misused. For example, a C union might store either an or a floating-point number in the same memory location, with the size determined by the larger type. In modern statically typed languages, union types emphasize safety and expressiveness through tagging and type narrowing. In , unions are denoted with the | operator, such as string | number, permitting functions to accept values of either type while restricting access to shared properties. Languages like implement safe tagged unions via enums, which support for exhaustive handling of variants, as in defining a Result<T, E> type that can hold either a success value or an error. Similarly, in functional languages like or , algebraic data types provide union-like sum types for modeling disjoint alternatives, such as shapes in a system (e.g., circle or rectangle). These features support advanced , occurrence typing, and , enhancing code reliability in applications from to .

Overview

Definition and purpose

A is a user-defined in programming languages that enables a single variable to store values of different types, with all possible members occupying the same contiguous block of and only one member holding a valid value at any given time. This overlapping storage contrasts with other composite types, as the size of a union is determined solely by the largest member, allowing efficient reuse of space for mutually exclusive data variants. The primary purpose of union types is to optimize memory usage by permitting the representation of variant data—such as a field that might hold an integer or a string—without allocating separate space for each possibility, which is particularly valuable in systems programming or embedded environments where resources are limited. Additionally, unions facilitate type punning, a technique for reinterpreting the binary representation of data as a different type to perform low-level manipulations, such as byte-order conversions or hardware register access. In certain contexts, they support polymorphism-like behavior by enabling the storage of disparate object types within a uniform structure, aiding in the design of flexible data representations. Unlike structs, which provide non-overlapping for all members and thus consume proportional to the sum of their sizes, unions enforce shared allocation to promote . Enumerations, by , serve to define named constants without inherent for variants, focusing instead on symbolic rather than polymorphic containment. Union types may be implemented as untagged variants, depending on external context to identify the active member, or tagged variants, incorporating a type discriminator for runtime safety. Overall, the key benefits of union types lie in their ability to deliver space efficiency and representational flexibility, allowing developers to model data that inherently varies in form while minimizing overhead.

Historical development

Early implementations of union types appeared in , released in 1964, where they were defined using the keyword to overlay storage for different data elements. The concept was further formalized in the programming language, introduced in 1968, where they were defined as "united modes" to allow variables to hold values of multiple types while incorporating modes for runtime and . This design emphasized expressive type systems, enabling programmers to declare unions that could dynamically determine and enforce the active type, influencing subsequent languages' approaches to type flexibility. In the early 1970s, union types evolved in systems-oriented languages for memory efficiency. Pascal, released in 1970, introduced tagged unions through variant records, which used a discriminant tag to safely distinguish among alternative types within a record, providing compile-time checks against invalid access. Concurrently, C, developed by Dennis Ritchie between 1971 and 1973, adopted untagged unions to facilitate low-level memory manipulation and data overlaying without runtime overhead, prioritizing portability and performance in Unix system programming. These developments in Pascal and C highlighted a divergence: tagged variants for safety versus untagged for raw control. The influence of these early unions extended to variant types in , where sum types—essentially tagged unions—emerged in languages like (1973) and later (1990) to model disjoint choices with exhaustive for error-free handling. In modern dynamic and typed languages, union types have expanded for better expressiveness in type hinting and structural typing. 8.0 (2020) added native union types for parameters, properties, and returns, allowing multiple type declarations separated by pipes. introduced union types in version 1.4 (2015), enabling values to be one of several types via the | operator for safer development. 3.10 (2021) simplified unions with the | syntax for annotations, reducing reliance on the typing.Union class. Meanwhile, Go has seen experimental proposals for restricted union types using type sets in interfaces, aiming to address limitations in handling variant data without full sum type adoption as of 2025.

Classification

Untagged unions

Untagged unions, also known as untagged or discriminated-free unions, are a form of type in programming languages that lack a discriminant or to specify which member of the union is currently active, placing the responsibility on the to maintain awareness of the active type. This design allows all possible members to overlay the same block of memory, enabling efficient space usage where only one is needed at a time, but it requires explicit tracking to avoid misinterpretation of the stored value. A key characteristic of untagged unions is their shared memory allocation, where the size of the union equals the size of its largest member, and assigning to one member overwrites the data of others, potentially leading to undefined behavior if the programmer accesses an incorrect member. For instance, in generic pseudocode, an untagged union might be declared as:
union Example {
    int integer;
    float real;
};
Here, setting u.integer = 1 would store the integer value in the shared memory, but reading u.real could produce garbage or erroneous results unless the programmer ensures the type matches the intended use. Untagged unions find common application in systems and performance-critical code, particularly for , where raw bytes are reinterpreted as different types to optimize access to registers or packed structures without additional overhead. For example, they enable efficient manipulation of bitfields in low-level device drivers by allowing direct overlay of scalar types onto structured representations. Historically, untagged unions have been a staple in C-family languages since the development of in the early 1970s by at , where they provided a lightweight mechanism for variant data handling in without the complexity of type tags. In contrast to tagged unions, which incorporate a for runtime type identification to enhance safety, untagged variants prioritize raw efficiency at the cost of potential errors.

Tagged unions

Tagged unions, also known as discriminated unions or sum types, pair a data structure with an explicit or enumerator field that indicates which member of the union is valid at . This serves as a discriminator, allowing the program to perform type checking before accessing the underlying data, thereby mitigating risks associated with incorrect variant interpretation. These structures are particularly prevalent in paradigms, where they form the basis of algebraic data types by representing a of mutually exclusive possibilities, each potentially carrying associated . The ensures that only the appropriate variant is accessed, enforcing either at in statically checked languages or via runtime . Unlike untagged unions, which lack this and depend on manual tracking, tagged unions systematically prevent invalid operations, reducing errors in variant handling. Common use cases include modeling optional or nullable values through types like Maybe or Option, which encapsulate either a present value or an absence indicator, and error-handling constructs such as Result or Either, distinguishing between successful outcomes and failure states with descriptive payloads. These applications promote robust code by making invalid states unrepresentable and facilitating exhaustive over all variants. For illustration, consider a representation of a simple for holding either an or a :
enum VariantType { [INTEGER](/page/Integer), [STRING](/page/STRING) };

struct TaggedValue {
    [VariantType](/page/The_Variant) tag;
    union {
        [int](/page/INT) integerValue;
        [char*](/page/Char) stringValue;
    } [payload](/page/Payload);
};
To initialize an variant:
TaggedValue tv;
tv.tag = [INTEGER](/page/Integer);
tv.payload.integerValue = 42;
Access requires tag verification:
if (tv.tag == [INTEGER](/page/Integer)) {
    // Safely use tv.payload.integerValue
} else {
    // Handle mismatch, e.g., raise error or default
}
This pattern guarantees that the payload is interpreted correctly, with the tag acting as a runtime sentinel.

Technical details

Memory representation

In union types, all members occupy the same memory region, with their storage overlapping such that each member begins at the initial offset of the union object, enabling only one member to hold a valid value at any time without individual allocations. The size of a union is determined by the size of its largest member, rounded upward as necessary to meet the alignment constraints of that member or the overall structure. For instance, a union containing a 4-byte and an 8-byte would have a size of 8 bytes to accommodate the larger type. The requirement of the matches that of its most strictly aligned member, ensuring the entire object can be placed at valid addresses; additional bytes may be inserted at the end to fulfill this, particularly for compatibility. Unions facilitate by allowing the bit pattern stored in one member to be reinterpreted as another member's type when accessed, a that is explicitly permitted in C to adhere to strict aliasing rules without invoking .

Type safety considerations

Union types, particularly untagged variants, pose significant type safety risks due to the potential for accessing an inactive member, which results in . In languages like and C++, reading from a union member that was not the most recently written to can lead to misinterpretation of the shared memory, causing bit-level misalignment, , or program crashes. This occurs because all members overlay the same memory region, and without an indicator of the active type, the compiler cannot enforce correct access, allowing erroneous code to compile and execute unpredictably. Tagged unions mitigate these issues by including a discriminator (such as an enum) to identify the active , but safety is not inherent; if the tag is not checked before accessing the data, tag mismatches can still trigger akin to untagged cases. For instance, assuming the wrong is active may lead to invalid memory reads or writes, exacerbating the risks of misalignment or invalid operations. To address this, developers must explicitly validate the tag prior to access, ensuring the correct member is used. Mitigation strategies include leveraging extensions and tools to enforce stricter rules. In , the -fstrict-aliasing flag enables optimizations based on the strict aliasing rule, which assumes pointers of different types do not the same object; however, improper use for can violate this, so disabling it with -fno-strict-aliasing is recommended when necessary to avoid optimization-induced bugs. Additionally, static analysis tools can detect potential misuse by tracking active members and flagging unchecked accesses. Best practices for safe union usage emphasize proactive measures: always initialize and maintain the tag in tagged unions to track the active variant; avoid unions for types with non-overlapping memory layouts or non-trivial constructors/destructors, as these complicate lifetime management; and prefer type-safe alternatives like C++'s std::variant, which tracks the active type at runtime and throws an exception on invalid access, preventing . In modern languages such as , enums serve as tagged unions with compile-time enforcement of variant handling via , providing without runtime checks through zero-cost abstractions that compile to efficient . While tags introduce performance trade-offs, such as additional overhead (typically 1-8 bytes for the discriminator depending on the enum ), they enable optimizations like improved branch prediction in switch statements on the tag, potentially reducing execution time in hot paths compared to unchecked untagged access. This balance favors tagged approaches in safety-critical code, where the modest space cost outweighs the risks of .

Language implementations

C and C++

In C, unions are declared using the syntax union name { member-declarations };, where the members are a sequence of declarations sharing the same memory location, and the size of the union is determined by the largest member, potentially with for . The union is untagged by default, meaning there is no built-in mechanism to track which member is active, requiring manual management by the . Unions in C are typically used for space-efficient storage of variant data or for , where the allows reinterpretation of the same bytes as different types. A common example is a to hold either an or a character array, as shown below:
c
union Data {
    [int](/page/INT) i;
    char str[10];
};

int main() {
    union Data d;
    d.i = 42;  // Initialize with [int](/page/INT)
    // Now access as char array ([type punning](/page/Type_punning))
    for ([int](/page/INT) j = 0; j < 10; ++j) {
        printf("%c", d.str[j]);
    }
    return 0;
}
This demonstrates , which is permitted in C when accessing through the type, allowing safe reinterpretation of the 's bytes as characters. Another practical use is detecting endianness via a with an and byte array:
c
union Endian {
    int value;
    unsigned char bytes[sizeof(int)];
};

int main() {
    union Endian e;
    e.value = 1;
    if (e.bytes[0] == 1) {
        // Little-endian
    } else {
        // Big-endian
    }
    return 0;
}
Such patterns rely on the union's overlapping storage but must adhere to strict aliasing rules, which prohibit direct pointer aliasing outside the union context to enable compiler optimizations. C++ inherits C's union syntax and semantics but introduces restrictions and extensions. Unions in C++ cannot have virtual functions, base classes, or be used as bases, and they support member functions including constructors and destructors under certain conditions. C++11 expanded support to allow non-POD (Plain Old Data) types in unions, provided at most one member has a non-trivial constructor or destructor, and exactly one such member is initialized in a constructor. Anonymous unions, standard in C++ for embedding members directly into enclosing structs without qualification (e.g., struct S { union { int a; float b; }; }; accesses s.a), are a GCC extension in C via unnamed fields. GCC also provides transparent unions as an extension, treating function arguments of union type as compatible with any member type for overloading. A key pitfall in both C and C++ is undefined behavior from violating strict aliasing, where accessing a union member via a pointer of an incompatible type (outside the union) can lead to optimization errors or crashes. Multi-threaded access to unions without synchronization risks data races, as the active member is not atomically tracked, potentially causing inconsistent reads. As a safer alternative in modern C++, std::variant (introduced in C++17) provides a type-safe union with compile-time type checking and runtime active-alternative tracking.

Rust

In Rust, unions provide a way to define untagged union types similar to those in C, where multiple fields overlap in the same memory location. The syntax for declaring a union mirrors that of a but uses the union keyword: union Name { field1: Type1, field2: Type2 }. For example:
rust
union MyUnion {
    f1: u32,
    f2: f32,
}
All fields share the same storage, so writing to one overwrites the others, and reading from a field requires an unsafe block to prevent undefined behavior from accessing invalid data. Initialization is safe, as in let u = MyUnion { f1: 1 };, but accessing fields demands explicit unsafe code, such as unsafe { let val = u.f1; }. This design ensures the borrow checker cannot verify memory safety automatically, placing responsibility on the programmer to track the active field. Unions have been stable since Rust 1.19.0 and remain unchanged in the 2021 edition, prioritizing explicit unsafety to avoid C-style runtime risks. For safe handling of variant data, Rust favors enums as tagged unions, which embed a discriminant tag to distinguish variants at compile time. The syntax is enum Name { Variant1(Type1), Variant2(Type2) }, where each variant can carry associated data. A canonical example is the standard Option<T> enum:
rust
enum Option<T> {
    None,
    Some(T),
}
Usage involves safe pattern matching with match, which the compiler enforces for exhaustiveness: all variants must be handled, or a default arm is required. For instance:
rust
let some_value = Some(42);
match some_value {
    Some(x) => println!("Got {}", x),
    None => println!("Nothing"),
}
This prevents invalid access, as the borrow checker ensures only the active 's data is borrowed. Enums implement zero-cost tagged unions, with no runtime overhead—the and payload are stored contiguously, matching the size of the largest plus the . This approach contrasts with raw unions by integrating safety into the , eliminating the need for unsafe blocks in typical use.

Python

In , union types are supported through the typing module for static type hinting, allowing variables, function parameters, and return values to be annotated as compatible with multiple types. Introduced in Python 3.5 via PEP 484, the Union type constructor enables annotations like Union[int, str], which indicate that a value can be of any of the specified types during static analysis. These hints are optional and have no effect on behavior, serving primarily to improve and enable tools for early detection. Starting with Python 3.10, PEP 604 simplified union syntax by overloading the bitwise OR operator (|) for types, allowing int | str as a direct alternative to Union[int, str] in annotations and even in isinstance and issubclass calls. This change enhances readability without requiring imports from the typing module for basic cases. For example, a function can be annotated as follows:
python
from typing import Union  # For Python < 3.10

def process_input(value: Union[int, str]) -> None:
    pass

# In Python 3.10+, equivalent to:
def process_input(value: int | str) -> None:
    pass
Such annotations help static type checkers infer compatibility, for instance, ensuring that process_input(42) or process_input("hello") are valid while rejecting incompatible types like process_input([1, 2]). Python's union types lack runtime enforcement or shared memory representation, distinguishing them from true unions in languages like C; instead, they are purely for static checking with tools such as mypy, which verifies annotations against code usage. At runtime, union-like behavior can be emulated using isinstance checks or by defining classes and dataclasses that wrap variants, akin to tagged unions, to enforce type-specific logic. For instance:
python
from dataclasses import dataclass
from [typing](/page/Typing) import [Union](/page/Union)

@dataclass
class IntWrapper:
    value: [int](/page/INT)

@dataclass
class StrWrapper:
    value: [str](/page/€STR)

# Emulate union at runtime
def handle_variant(variant: [Union](/page/Union)[IntWrapper, StrWrapper]) -> None:
    if isinstance(variant, IntWrapper):
        print(f"Integer: {variant.value}")
    elif isinstance(variant, StrWrapper):
        print(f"String: {variant.value}")
This approach allows runtime discrimination but requires explicit implementation, as Python's dynamic nature does not natively support discriminated unions. Historically, before explicit unions, developers relied on the Any type from the typing for flexible annotations, but unions marked a shift toward more precise static , reducing over-reliance on Any and improving checker accuracy in large codebases. The 3.10 syntax further streamlined adoption, aligning 's more closely with modern idioms while preserving .

TypeScript

In TypeScript, union types enable a value to be one of several possible types, providing structural typing that enhances in JavaScript development. This feature allows developers to model scenarios where a variable or property can hold values of multiple types, such as strings or , without runtime enforcement since TypeScript is a compile-time superset of . The syntax for declaring a union type uses the (|) to separate constituent types, either as a named type alias or inline. For example, type ID = string | number; defines a type alias for an identifier that can be either a string or a number, while inline usage appears as function log(id: string | number) { ... }. Unions can combine primitive types, object types, or other unions, but access to properties is limited to those common across all members to prevent type errors. Type narrowing refines the inferred type within conditional blocks using type guards, such as typeof checks or in operators, allowing safe access to type-specific members. For instance, in a function handling a string | number parameter, an if (typeof value === "string") block narrows value to string, enabling methods like toUpperCase(). Discriminated unions extend this by using a shared literal-type discriminant property for precise narrowing via switches or if-statements. A common pattern involves objects with a kind or type field:
typescript
type Shape = 
  | { kind: "circle"; radius: number }
  | { kind: "square"; side: number };
function getArea(shape: Shape) {
  switch (shape.kind) {
    case "circle": return Math.PI * shape.radius ** 2;
    case "square": return shape.side ** 2;
  }
}
This ensures exhaustiveness checking when paired with the never type in a default case, catching unhandled variants at compile time. Unions integrate seamlessly with interfaces and function overloads; for example, an interface might declare a property as status: "loading" | "success" | "error", restricting values to those literals and improving autocomplete in editors like VS Code via enhanced IntelliSense. In function signatures, unions support overloads by specifying return types based on input narrowing, such as handling mixed arrays. Since unions are erased during compilation to plain , there is no overhead, but JavaScript's dynamic nature allows through arrays or objects. Introduced in 3.4, const assertions (as const) enhance unions by preserving literal types in expressions, preventing widening to broader types like string and enabling precise union construction from constants. For example, const directions = ["north", "east"] as const; infers type Directions = "north" | "east";, useful for creating closed literal unions without manual enumeration. Subsequent versions, including 4.0, improved related inference for variadic tuples and unions, facilitating more robust type combinations in advanced scenarios.

PHP

Union types in PHP, introduced in version 8.0, enable developers to specify multiple acceptable types for function parameters, class properties, and return values, enhancing in this dynamically typed language commonly used for . This feature addresses limitations in PHP's prior by allowing declarations like int|string, where the vertical bar (|) separates individual types. The mixed type, also added in PHP 8.0, serves as a wildcard encompassing any type, including unions, and can be used in these declarations to indicate broad compatibility. Union types are supported in function parameters, class properties, and return types, but PHP does not permit standalone union type declarations for local variables. For instance, a class property can be declared as public [int](/page/INT)|[float](/page/Float) $value;, allowing the property to hold either an or a value. Similarly, functions can specify union types in parameters and returns, such as function processData([mixed](/page/mixed)|[array](/page/Array) $input): [string](/page/String)|[int](/page/INT) { return gettype($input) === 'array' ? 'processed' : 42; }, where type checking might use built-in functions like gettype() for validation. These declarations promote clearer code intent without requiring extensive documentation annotations. Type enforcement for union types occurs primarily at runtime, throwing a TypeError if a value does not match any permitted type in the declaration, though this is partial due to PHP's inherent weak typing system. Developers can enable stricter checking via declare(strict_types=1); at the file level, but backward compatibility with PHP's loose type coercion is maintained to avoid breaking existing codebases. Limitations include prohibitions on combining singleton types like false and true in a union (use bool instead) and excluding void or never from unions. In 8.1 and later, union types integrate with readonly properties, which can only be initialized once (typically in the constructor) and cannot be modified afterward, providing immutable typed data structures like public readonly string|[int](/page/INT) $id;. This combination supports safer data transfer objects in web applications, building on the union type foundation from 8.0.

Go and

In Go, there are no native types, with developers instead emulating them using the empty interface interface{} to hold values of any type, combined with type switches for runtime type inspection and handling. For example, a value can be assigned to an interface{} variable and then inspected via a type switch:
go
var i interface{} = 42
switch v := i.(type) {
case int:
    fmt.Println("It's an integer:", v)
default:
    fmt.Println("Unknown type")
}
This approach sacrifices compile-time type safety for flexibility, as the compiler cannot enforce which types might be stored. Since the introduction of generics in Go 1.18, type parameters can use union-like constraints to define sets of allowable types, such as int64 | float64, enabling more type-safe generic functions that approximate variant handling without full union semantics for variables. For instance, a generic sum function might constrain its value type to numeric unions:
go
func SumIntsOrFloats[K comparable, V int64 | float64](m map[K]V) V {
    var s V
    for _, v := range m {
        s += v
    }
    return s
}
However, these constraints apply only to generic parameters and do not provide true discriminated unions at the value level. Go's design philosophy prioritizes simplicity and explicitness, avoiding complex features like native unions to reduce cognitive load and potential errors in concurrent code. As of November 2025, ongoing proposals such as issue #70752 seek to enable finite type sets as union types via extended constraints, but none have been adopted in the language specification. Swift, in contrast, supports tagged unions natively through enumerations (enums) with associated values, allowing each case to carry data of different types while ensuring via exhaustive . This feature models sum types, where the enum acts as a discriminated , storing a tag (the case) alongside optional payload data. A example is the Result type, commonly used for error handling:
swift
enum Result<T, E> {
    case success(T)
    case error(E)
}

let result: Result<String, [Error](/page/Error)> = .success("Hello")
occurs via switch statements, which the enforces to cover all cases, preventing surprises:
swift
switch result {
case .success(let [value](/page/Value)):
    [print](/page/Print)("Success: \(value)")
case .error(let [error](/page/Error)):
    [print](/page/Print)("Error: \(error)")
}
This exhaustive checking promotes handling of variants, integrating seamlessly with optionals (themselves an enum with associated values) for representing possibly absent data. Swift's enums thus provide a robust alternative to raw unions, emphasizing compile-time guarantees over Go's flexibility.

References

  1. [1]
    [PDF] Programming with Union, Intersection, and Negation Types - l'IRIF
    In this essay we present the use of set-theoretic types in programming languages and outline their theory. Set theoretic types include union types t1 ∨ t2, ...
  2. [2]
  3. [3]
    Handbook - Unions and Intersection Types - TypeScript
    A union type describes a value that can be one of several types. We use the vertical bar ( | ) to separate each type.Union Types · Discriminating Unions · Union Exhaustiveness...Missing: programming | Show results with:programming
  4. [4]
    The union data type - Emory CS
    }; Meaning: A union data structure is a number of memory cells used to store any one of the variables specified in the union structure. In other words:
  5. [5]
    5.8.2 Unions And Bit-Fields
    In contrast, a union typically specifies two or more fields of different types but only allocates enough memory to contain the largest. All fields share this ...
  6. [6]
    C Programming Course Notes - Structures, Unions, and Enumerated ...
    Unions are declared, created, and used exactly the same as struts, EXCEPT for one key difference: · This means that all fields in a union share the same space, ...
  7. [7]
    [PDF] Structs, Unions, and Enums
    • Enumeration: data type consisting of a set of named values called enumerators. E.g.: – enum Suit {Spades, Diamonds, Clubs, Hearts} suit;. • In C, an enum ...
  8. [8]
    Structures, Unions, and Enumerations
    A union is similar to a struct, except that only one of the fields may contain a value at any time. Without type tags to tell us which field contains a value, ...Missing: data | Show results with:data
  9. [9]
    [PDF] Informal Introduction to ALGOL 68 : Revised Edition
    The algorithmic language, ALGOL 68, stands as a major product of the. International Federation for Information Processing, an organization now in its second ...
  10. [10]
    Revised Report on the Algorithmic Language Algol 68
    This is a translation of the Algol 68 Revised Report into HTML, for distribution with Algol 68 Genie, an Open Source Algol 68 interpreter …
  11. [11]
    [PDF] Stanford Pascal Verifier User Manual - DTIC
    There is a TAG function for determining the tag of a union variable, and there are selection and construction functions. The UNION type declaration has the form.
  12. [12]
    [PDF] The Development of the C Language - Nokia
    Dennis Ritchie turned B into C during 1971-73, keeping most of B's syntax while adding types and many other changes, and writing the first compiler. Ritchie, ...
  13. [13]
    A Very Early History of Algebraic Data Types - Hillel Wayne
    Sep 25, 2025 · Sum types are “tagged unions”, things like Int + Nothing , Result + ErrorType , or Address + Number + Email . They are a choice between several ...
  14. [14]
    PHP: PHP 8.0.0 Release Announcement
    PHP 8.0 includes named arguments, union types, attributes, constructor property promotion, match expression, nullsafe operator, JIT, and type system ...Missing: 2020 | Show results with:2020
  15. [15]
    Documentation - TypeScript 1.4
    Union types are a powerful way to express a value that can be one of several types. For example, you might have an API for running a program that takes a ...Union types · let declarations · const declarations · Type Guards
  16. [16]
    What's New In Python 3.10 — Python 3.14.0 documentation
    A new type union operator was introduced which enables the syntax X | Y . This provides a cleaner way of expressing 'either type X or type Y' instead of using ...
  17. [17]
    Rust Release Notes
    Sep 18, 2025 · The 2024 Edition is now stable. See the edition guide for more ... Allow associated types to be used as union fields. Allow Self ...
  18. [18]
    proposal: spec: finite type set interface as union type #70752 - GitHub
    Dec 10, 2024 · This proposal suggests permitting a restricted set of type constraints to be usable as Union types.
  19. [19]
    What are pros and cons of tagged vs untagged union-types?
    Jul 12, 2023 · A pure untagged union does no type checking so you can interpret it's contents as type A when it is type B. In most languages this is undefined ...
  20. [20]
    Unions (GNU C Language Manual)
    A union type defines alternative ways of looking at the same piece of memory. Each alternative view is defined with a data type, and identified by a name.
  21. [21]
    Are there any uses for untyped unions(w/out a type tag)?
    Dec 9, 2011 · One use for untagged unions is to allow easy access to smaller parts of a larger type: union reg_a { uint32_t full; struct { /* little-endian in this example * ...Difference union types and discriminated unions typescript/F#What are union types and intersection types? - Stack OverflowMore results from stackoverflow.com
  22. [22]
    Why do we need C Unions? - Stack Overflow
    Oct 31, 2008 · Unions are particularly useful in Embedded programming or in situations where direct access to the hardware/memory is needed.Purpose of Unions in C and C++ - Stack OverflowDifference between a Structure and a Union - Stack OverflowMore results from stackoverflow.comMissing: history | Show results with:history
  23. [23]
    Discriminated Unions - F# | Microsoft Learn
    Discriminated unions provide support for values that can be one of a number of named cases, possibly each with different values and types.
  24. [24]
    Stream Types | Proceedings of the ACM on Programming Languages
    Jun 20, 2024 · Sum types in λST, written s + t, are tagged unions: a stream of type s + t is either a stream of type s or a stream of type t, and a ...
  25. [25]
    Algebraic data types - CS 242
    Algebra of ADTs. Product types and sum types are collectively called “algebraic” data types because they have algebraic properties similar to normal integers.ADTs by example · Variants · ADT theory · Product types
  26. [26]
    Overloading, Eta Expansion, and Extensible Data Types in F
    Unlike sum types (or tagged unions), untagged unions are not always equipped by an explicit elimination construct. When first introduced by MacQueen et al ...
  27. [27]
    3.2.4. Algebraic Data Types · Functional Programming in OCaml
    The sum types come from the fact that a value of a variant is formed by one of the constructors. The product types come from that fact that a constructor can ...
  28. [28]
    [PDF] System Verilog Tagged Unions and Pattern Matching - Accellera
    Tagged unions can be simulated by manual coding with existing structs and unions, but this is not type-safe, and they are generally not as concise or visually ...<|control11|><|separator|>
  29. [29]
  30. [30]
    The Strict Aliasing Situation is Pretty Bad - Embedded in Academia
    Mar 15, 2016 · It is possible to violate the strict aliasing rule even without casting pointers, by taking pointers to different members of a union. regehr ...
  31. [31]
  32. [32]
    Defining an Enum - The Rust Programming Language
    Enums give you a way of saying a value is one of a possible set of values. For example, we may want to say that Rectangle is one of a set of possible shapes.Missing: zero cost
  33. [33]
    Union Declarations | Microsoft Learn
    Jul 26, 2023 · A union declaration specifies a set of variable values and, optionally, a tag naming the union. The variable values are called members of the union and can ...
  34. [34]
    Type Punning, Strict Aliasing, and Optimization
    Jun 11, 2013 · Now we use the type punning feature of unions to read out the other representation: 1. 2. 3. 4. 5. 6. 7. 8. uint64_t c2 ( const uint16_t *buf) {.
  35. [35]
    What is the Strict Aliasing Rule and Why do we care? - GitHub Gist
    The compiler and optimizer are allowed to assume we follow the aliasing rules strictly, hence the term strict aliasing rule.
  36. [36]
    Unnamed Fields (Using the GNU Compiler Collection (GCC))
    GCC allows you to define a structure or union that contains, as fields, structures and unions without names.
  37. [37]
    Unions - The Rust Reference
    Unions in Rust share common storage, where writes to one field can overwrite others. Size is based on the largest field. There is no notion of an active field.
  38. [38]
    union - Rust
    A union looks like a struct in terms of declaration, but all of its fields exist in the same memory, superimposed over one another.
  39. [39]
    Enumerations - The Rust Reference
    An enumeration, also referred to as an enum, is a simultaneous definition of a nominal enumerated type as well as a set of constructors.<|control11|><|separator|>
  40. [40]
    typing — Support for type hints — Python 3.14.0 documentation
    The `typing` module provides runtime support for type hints, which are not enforced by the runtime but used by tools like type checkers.3.9.24 · Static Typing with Python · Python 3.10.19 documentation · Specification
  41. [41]
    PEP 604 – Allow writing union types as X | Y
    This PEP proposes overloading the | operator on types to allow writing Union[X, Y] as X | Y, and allows it to appear in isinstance and issubclass calls.Missing: 2021 | Show results with:2021
  42. [42]
    Documentation - Everyday Types - TypeScript
    A union type is a type formed from two or more other types, representing values that may be any one of those types. We refer to each of these types as the ...Object Types · Enums · Narrowing · Symbols
  43. [43]
    Documentation - TypeScript 3.4
    const assertions. TypeScript 3.4 introduces a new construct for literal values called const assertions. Its syntax is a type assertion with const in place of ...
  44. [44]
    Documentation - TypeScript 4.0
    TypeScript 4.0 brings two fundamental changes, along with inference improvements, to make typing these possible.
  45. [45]
    Type declarations - Manual - PHP
    Union types ¶​​ It is not possible to combine the two singleton types false and true together in a union type. Use bool instead. Prior to PHP 8.2.
  46. [46]
    PHP RFC: Union Types 2.0
    Sep 2, 2019 · A “union type” accepts values of multiple different types, rather than a single one. PHP already supports two special union types.
  47. [47]
    Type System - Manual - PHP
    Individual types which form the union type are joined by the | symbol. Therefore, a union type comprised of the types T , U , and V will be written as T|U|V .
  48. [48]
    Properties - Manual - PHP
    Readonly properties ¶. As of PHP 8.1.0, a property can be declared with the readonly modifier, which prevents modification of the property after initialization.
  49. [49]
    Effective Go - The Go Programming Language
    A switch can also be used to discover the dynamic type of an interface variable. Such a type switch uses the syntax of a type assertion with the keyword type ...Missing: emulation | Show results with:emulation
  50. [50]
    Tutorial: Getting started with generics
    Generics in Go allow functions/types to work with any of a set of types provided by calling code, using type parameters and constraints.
  51. [51]
    Enumerations | Documentation - Swift.org
    You can define Swift enumerations to store associated values of any given type, and the value types can be different for each case of the enumeration if needed.