Sök…


Introduktion

Den mest triviala datastrukturen, efter singelvärde, är tupeln.

Syntax

  • (A, B, C) // en tre-tuple (en tuple med tre element), vars första element har typ A, andra typ B och tredje typ C
  • (A, B) // en två-tupel, vars två element har typ A respektive B
  • (A,) // en en-tuple (notera släpet , ), som bara innehåller ett enda element av typ A
  • () // den tomma tupeln, som är både en typ och den typens enda element

Tupeltyper och tupelvärden

Rostknölar, som på de flesta andra språk, är listor i fast storlek vars element alla kan vara av olika slag.

// Tuples in Rust are comma-separated values or types enclosed in parentheses.
let _ = ("hello", 42, true);
// The type of a tuple value is a type tuple with the same number of elements.
// Each element in the type tuple is the type of the corresponding value element.
let _: (i32, bool) = (42, true);
// Tuples can have any number of elements, including one ..
let _: (bool,) = (true,);
// .. or even zero!
let _: () = ();
// this last type has only one possible value, the empty tuple ()
// this is also the type (and value) of the return value of functions
// that do not return a value ..
let _: () = println!("hello");
// .. or of expressions with no value.
let mut a = 0;
let _: () = if true { a += 1; };

Matchande tupelvärden

Rust program använder mönstermatchning stor utsträckning för att dekonstruera värden, oavsett om du använder match , if let , eller dekonstruera let mönster. Tuples kan dekonstrueras som du kan förvänta dig med match

fn foo(x: (&str, isize, bool)) {
    match x {
        (_, 42, _) => println!("it's 42"),
        (_, _, false) => println!("it's not true"),
        _ => println!("it's something else"),
    }
}

eller med if let

fn foo(x: (&str, isize, bool)) {
    if let (_, 42, _) = x {
        println!("it's 42");
    } else {
        println!("it's something else");
    }
}

Du kan också binda inuti tupeln med let konstruktion

fn foo(x: (&str, isize, bool)) {
    let (_, n, _) = x;
    println!("the number is {}", n);
}

Titta inuti tuplorna

För att komma åt element i en tupel direkt kan du använda formatet .n att komma åt det n te elementet

let x = ("hello", 42, true);
assert_eq!(x.0, "hello");
assert_eq!(x.1, 42);
assert_eq!(x.2, true);

Du kan också delvis flytta ur en tupel

let x = (String::from("hello"), 42);
let (s, _) = x;
let (_, n) = x;
println!("{}, {}", s, n);
// the following would fail however, since x.0 has already been moved
// let foo = x.0;

Grunderna

En tupel är helt enkelt en sammanlänkning av flera värden:

  • av möjligen olika typer
  • vars antal och typer är statiskt känt

Till exempel är (1, "Hello") en 2 element-tupel sammansatt av en i32 och en &str , och dess typ betecknas som (i32, &'static str) på liknande sätt som dess värde.

För att få tillgång till ett element i en tupel använder man bara sitt index:

let tuple =  (1, "Hello");
println!("First element: {}, second element: {}", tuple.0, tuple.1);

Eftersom tupeln är inbyggd är det också möjligt att använda mönstermatchning på tuples:

match (1, "Hello") {
    (i, _) if i < 0 => println!("Negative integer: {}", i),
    (_, s) => println!("{} World", s),
}

Speciella fall

0-elementtupeln: () kallas också enhet , enhetstyp eller singletontyp och används för att beteckna frånvaron av meningsfulla värden. Det är standardtypen för funktioner (när -> inte anges). Se även: Vilken typ är "typen ()" i Rust? .

1 elementet tuple: (a,) , med den efterföljande kommaet, betecknar en 1 element tuple. Formen utan komma (a) tolkas som ett uttryck inneslutet inom parentes och utvärderas till bara a .

Och medan vi är på det accepteras alltid efterkommande kommatecken: (1, "Hello",) .


begränsningar

Rostspråket i dag stöder inte variadier , förutom tupler. Därför är det inte möjligt att helt enkelt implementera ett drag för alla tuplingar och som ett resultat implementeras standarddragen endast för tupplar upp till ett begränsat antal element (idag, upp till 12 inkluderade). Tuples med fler element stöds, men implementerar inte standarddragen (även om du kan implementera dina egna egenskaper för dem).

Denna begränsning kommer förhoppningsvis att upphävas i framtiden.

Packa upp tuples

// It's possible to unpack tuples to assign their inner values to variables
let tup = (0, 1, 2);
// Unpack the tuple into variables a, b, and c
let (a, b, c) = tup;

assert_eq!(a, 0);
assert_eq!(b, 1);

// This works for nested data structures and other complex data types
let complex = ((1, 2), 3, Some(0));

let (a, b, c) = complex;
let (aa, ab) = a;

assert_eq!(aa, 1);
assert_eq!(ab, 2);


Modified text is an extract of the original Stack Overflow Documentation
Licensierat under CC BY-SA 3.0
Inte anslutet till Stack Overflow