タプル

数学におけるタプル

集合論では n 組 (n-tuple) とは n 個の対象 a₁, a₂, ..., aₙ の順序づけられた組であり、普通、括弧でくくって (a₁, a₂, a₃, ..., aₙ) のように書かれる。 タプルが順序づけられているということは、2 つの n 組 (a₁, a₂, ..., aₙ) と (b₁, b₂, ..., bₙ) が等しいとされるのが、対応する位置の要素がすべて等しいとき、すなわち (a₁ = b₁) ∧ (a₂ = b₂) ∧ ... ∧ (aₙ = bₙ) であるとき、かつそのときに限ることを意味する。 タプルと直積集合には密接な関係があり、n 組の i 番目の対象が集合 Aᵢ の要素とみなされるならば、n 組は直積集合 A₁ × A₂ × ... × Aₙ の要素である。 
2 つの要素 a ∈ A, b ∈ B の順序づけられた組 (a, b) ∈ A × B は特に順序対 (ordered pair) と呼ばれる。 形式上は逆に、この順序対を元とすることによって一般の n 組 (n ≧ 2) を、例えば (a₁, a₂, a₃, ..., aₙ) = (...((a₁, a₂), a₃), ..., aₙ) のようにして構成的に定めることもできる。
タプルは様々な数学概念を定義するためにも利用される。 例えば、有限オートマトンは、入力アルファベットの有限集合 Σ, 状態の有限集合 S, 初期状態 s₀ ∈ S, 遷移関数 δ : Σ × S → S, 受理状態の有限集合 F ⊆ S の 5 つ組 (quintuple, 5-tuple) (Σ, S, s₀, δ, F) として定められ、有向グラフは、頂点集合 V と辺の集合 A ⊆ V × V の順序対 (V, A) として定められる。 
なお数ベクトルも同じように要素の順序づけられた並びとして表されるが、数学の形式上、ある線形空間の要素とみなされるベクトルは実数、複素数など同じ体の要素からなるものである。 対して、タプルは任意の集合の要素を並べただけのずっと一般的な概念であるといえる。

タプル型

型システム的には、代数的データ型でいう直積型そのものであり、C#、C++、Haskell、Kotlin、ML、Python、Scala、TypeScript といった多くのプログラミング言語にタプル型がある。いくつかは (x, y) といったような構文でタプル型の値を直接記述できる。
動的な型付けを持つ言語では、コンテナ型を使うことで済まさせている場合もある。一方でPythonのように、長さを後から変えられないばかりでなく要素を変えることもできないというような、タプル専用のオブジェクトを用意している場合もある。
静的な型付けを持つ言語の場合、リスト型やコンテナ型の要素は、基本的になんらかの「同じ」型でなければならないので、それらの集積型をタプルの目的に流用することは不可能であり、そのためこの節の冒頭のようにタプルないし同等のものをサポートしていることが多い。

Lispの場合

（伝統的な）Lispの場合、基本的には線型リストを作るためのデータ構造であるコンスセル（cons cell）を、要素2個のタプル（二ツ組）に流用する。cons, car, cdr というリスト操作用の関数もそのまま流用される。格納するデータの型に制限はない。
  (cons car部のデータ cdrのデータ)
car部のデータを取り出すには関数 car を使い、cdr部のデータを取り出すには関数 cdr を使う。
  (setq x (cons 'A 1))
  (setq a (car x))     ; a には 'A が入る
  (setq b (cdr x))     ; b には 1 が入る
また、
  (list データ1 データ2 データ3 … データN)
という関数呼び出しは、
  (cons データ1 (cons データ2 (cons データ3 … (cons データN nil) … )))
という形、すなわち、car部にデータがあり、cdr部が後続のコンスセルになっており、最後のcdr部分を nil という特殊な記号で終端させた二分木を返す。このような形式の二分木は「ちゃんとした」リストになっていると言えることから、「（プロパー）リスト」などという。

Python におけるタプル

Python におけるタプルは、任意の要素数の値をまとめてあたかもひとつの値のように扱う機能である。
タプルでは要素の型 （数値型、文字列型など）の同一性は不問であり、たとえば ('A', 1) という文字列と整数をひと塊として変数に代入できる。
x = ('A', 1)
Pythonはゼロまたはひとつの要素となるタプルも認めており、とくに1要素のタプルはプログラミング言語としては珍しい。普通、そのようなものは計算の優先順位を変更するため、または1引数関数の引数を括るための括弧と区別できないからである。Pythonの場合、要素に続けてカンマを置くことで識別する。カンマを忘れるとタプルとして認識できなくなってしまうということでもある。
x = (1,)        # 1要素の場合。()内末尾のカンマに注意y = ()        # 0要素の場合。関数型言語ではユニットとして知られているが、タプルとは別に語られる
タプルは関数の返り値として使うこともできる。これによって、複数の値を返す関数を実現することができる。
def func():
  return ('A', 1)x = func()        # x には ('A', 1) が入る
また、タプルは下記のようにして個別の要素を分離する。
x = ('A', 1)(a, b) = x        # a には 'A'、b には 1 が入る

Haskellにおけるタプル

ML系の関数型言語にほぼ共通して言えることとして、再帰的なデータ型であるリストとは異なり、タプルはそうでない点がある。また、リストの要素は単一の型のみを許容するのに対し、タプルの要素は型を問わない。これもデータ構造が再帰的か否かという点に由来するものである。また、要素へのアクセスはパターンマッチングか、先頭要素とその次の要素程度までを求める関数しかない。再帰的に定義されていないため、再帰関数で手繰ることも難しい(リストなら先頭と残りに分離することで容易に行える)。にもかかわらず、多くの関数型言語は60前後の要素まで許容されている。
Haskellでは、Pythonに類似した方法で利用できる部分もある。Pythonなどに影響を与えた側なので当然といえば当然である。
x = ('A', 1)(a, b) = x        -- a には 'A'、b には 1 が入る。パターンマッチの例
アクセス関数としては、第1要素を取得するfstと、第2要素を取得するsndがある。
x = ('A', 1)a = fst x        -- a には 'A' が入るb = snd x        -- b には 1 が入る
Haskellでは、2要素のタプルはデータ構築子 (,) で定義される。3要素なら (,,) で、最大の要素数は64であるため、これはカンマが63個並ぶことになる。以下はどちらも同じタプルが生成される。
x = ('A', 1)y = (,) 'A' 1
もちろんセクション(演算子の部分適用)も可能である。
x = (, 'A')f y = x        -- y に1を与えたとすれば、fは (1, 'A') を返す
セクションなどでは、要素数に応じた構築子を使わなければならない。たとえば要素数が3ならば
f x y = (,,) x y 3-- これは以下と等価であるf x y = (x, y, 3)
ユーティリティ関数としてcurryとuncurryが定義されている。いずれも2-tupleしか受け付けない。
curry id 'A' 1       -- id ('A', 1) と等価で、curryは ('A', 1) を返すuncurry (+) (1,42)        -- (+) 1 42 と等価で、これは 1 + 42 とも等価であるから、uncurryは43を返す

C# におけるタプル

C#言語におけるタプル(System.Tupleクラス)は.NET Framework 4.0からサポートされた総称型のコンテナのひとつ。CLIで定義されたクラスであるためVisual Basic .NETでも同様に使用可能である。
var tuple1 = new Tuple<int>(1);var tuple2 = new Tuple<string, int>("one", 1);
それぞれの値の取り出しは、Item1, Item2, ... にアクセスすることで行える。Pythonと違い、Tuple型で返したからといって複数の戻り値を返す関数とはならない。
var tuple2 = new Tuple<string, int>("one", 1);string word = tuple2.Item1;int number = tuple2.Item2;
他にも同様の総称型を持つ言語では、同様にしてタプルを使えるかもしれない。
C#7.0からサポートされたタプル構文では、より簡易な記法でタプルの取り扱いが可能となった。
また、分解構文をサポートしたため、多値戻り値が可能となった。
タプル構文ではSystem.ValueTuple構造体が使用される。
// 名前なしタプルvar tuple1 = ("one", 1);string word1 = tuple1.Item1;int number1 = tuple1.Item2;// 名前付きタプルvar tuple2 = (key: "one", value: 1);string word2 = tuple2.key;int number2 = tuple2.value;// タプルの分解(string str, int num) = tuple1;

TypeScript におけるタプル

TypeScript 1.3 から対応した。
var tuple: [string, number] = ["one", 1];

関係データベースにおけるタプル

関係データベースの理論である関係モデルでは、タプル（組）とはある関係（リレーション）を表（テーブル） として表したときの1つの行にあたり、形式的には、上述のタプルと同様に属性名を添字とした属性の型の直積集合の要素として表される。