トラック
/
Swift
Swift
/
演習
/
サンタのSwiftyな助手
サンタのSwiftyな助手

サンタのSwiftyな助手

学習演習

はじめに

タプルは、複数の値を1つの複合的な値にまとめます。 配列とは異なり、タプル内の値は同じ型である必要はなく、タプルのサイズは作成時に固定されます。

タプルを作るには、カンマで区切った値を括弧(())で囲みます。

let order = ("biscuits", 2.99, 3)

型注釈を明示的に指定することもできます。

let order: (String, Double, Int) = ("biscuits", 2.99, 3)

名前のないタプルから個々の要素を取り出すには、0から始まるインデックスの構文(.0、.1など)を使います。

let item = order.0     // "biscuits"
let quantity = order.2 // 3

名前付きタプル

タプルを定義するときに、個々の要素に名前を付けられます。

let order = (item: "biscuits", price: 2.99, quantity: 3)

要素に名前を付けるとコードが読みやすくなり、ラベルを使ったドット記法で要素にアクセスできるようになります。

let item = order.item         // "biscuits"
let quantity = order.quantity // 3

型注釈の中に要素名を含めることもできます。

let order: (item: String, price: Double, quantity: Int) = (item: "biscuits", price: 2.99, quantity: 3)

タプルの変更

タプルが変数(var)として宣言されていれば、その要素を更新できます。

var order = ("biscuits", 2.99, 3)
order.0 = "cookies"
order.1 = 1.99
order.2 = 5

print(order)
// Prints ("cookies", 1.99, 5)

複数の値を返す

Swiftの関数は1つの値しか返せませんが、タプルを返せば、関数から複数の値をまとめて返すことができます。

func divide(_ dividend: Int, by divisor: Int) -> (quotient: Int, remainder: Int) {
    let quotient = dividend / divisor
    let remainder = dividend % divisor
    return (quotient, remainder)
}

let result = divide(14, by: 4)
print("Quotient: \(result.quotient), Remainder: \(result.remainder)")
// Prints "Quotient: 3, Remainder: 2"

タプルの分解

タプルの値を、個別の定数や変数に分解(アンパック)できます。

let order = ("biscuits", 2.99, 3)
let (item, price, quantity) = order

print(item) // Prints "biscuits"

タプルの分解は、for-inループの中でもそのまま使えます。

let orders = [("biscuits", 2.99, 3), ("cookies", 1.99, 5)]

for (item, price, quantity) in orders {
    print("Item: \(item), Price: \(price), Quantity: \(quantity)")
}

説明

サンタクロースの物流部門で働くエルフは、上司からシステムのソフトウェアをアップグレードするための2つの仕事を任されました。

1. おもちゃの名前を取得する

システムは、データベースからおもちゃの名前を取得できる必要があります。 データベースは、(name: String, quantity: Int)型のタプルでできています。

タプル(name: String, quantity: Int)を受け取る関数getName(_:)を実装しましょう。

let toy = (name: "Doll", quantity: 10)
getName(toy)
// Returns "Doll"

2. データベースに新しいおもちゃを追加する

おもちゃの市場は移り変わりが早く、人気の商品もめまぐるしく変わります。 そのため、新しいおもちゃを作成する関数が必要です。

おもちゃの名前を持つ引数nameと、おもちゃの数量を持つ引数amountを受け取る関数createToy(name:amount:)を実装しましょう。

createToy(name: "Doll", amount: 10)
// Returns (name: "Doll", amount: 10)

3. おもちゃの数量を更新する

サンタの工房のエルフたちは絶えずおもちゃを作り続けているので、サンタはおもちゃごとの数量を把握しておく必要があります。 そのために、システムはデータベース内のおもちゃの数量を更新できる必要があります。

次の引数を受け取る関数updateQuantity(_:toy:Amount:)を実装しましょう。

  • toysは、タプル(name: String, quantity: Int)の配列を持ちます。
  • toyは、更新するおもちゃの名前を持ちます。
  • amountは、おもちゃの新しい数量を持ちます。

おもちゃはすでにデータベースにあると想定してよく、その確認は必要ありません。

let toys = [(name: "Doll", quantity: 10), (name: "Car", quantity: 5), (name: "Train", quantity: 3)]
updateQuantity(toys, toy: "Doll", amount: 15)
// Returns [(name: "Doll", quantity: 15), (name: "Car", quantity: 5), (name: "Train", quantity: 3)]

4. おもちゃにカテゴリーキーを追加する

サンタは、データベース内のおもちゃを分類できるようにしたいと考えています。 こうすると、配達が必要なときに目的のおもちゃをすぐ見つけられ、データベース内のおもちゃを並べ替えることもできます。

しかし、システムを最初に実装したとき、カテゴリーキーは忘れられていました。 そこで今度は、システムがデータベース内のおもちゃにカテゴリーキーを追加できる必要があります。

次の引数を受け取る関数addCategory(_:category:)を実装しましょう。

  • toysは、タプル(name: String, quantity: Int)の配列を持ちます。
  • categoryは、おもちゃに追加するカテゴリーキーを持ちます。

おもちゃはすでにデータベースにあると想定してよく、その確認は必要ありません。 また、おもちゃにカテゴリーキーがまだないことも想定してかまいません。

let toys = [(name: "Car", quantity: 5), (name: "Train", quantity: 3)]
addCategory(toys, category: "Vehicle")
// Returns [(name: "Car", quantity: 5, category: "Vehicle"), (name: "Train", quantity: 3, category: "Vehicle")]
GitHubで編集する リンクは新しいウィンドウまたはタブで開きます
Swift Exercism

サンタのSwiftyな助手を始める準備はできましたか?

Exercismに登録すれば、35個のコンセプト116個の演習、そして本物の人間によるメンタリングとともに、Swiftを学んでマスターできます。すべて無料です。