12. How to customize subscripting in Swift?

It will take about 1 minutes to finish reading this article.

In Swift, you can customize subscripting, which allows you to access elements in a collection, list, or other types using subscript syntax. Here is an example of how to customize subscripting:

Example 00:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
struct MyList {
private var list: [Int] = [1, 2, 3, 4, 5]

subscript(index: Int) -> Int? {
guard index >= 0 && index < list.count else {
return nil
}
return list[index]
}
}

var myList = MyList()
if let value = myList[2] {
print("Value at index 2: \(value)")
} else {
print("Index out of range")
}

In this example, we define a structure called MyList and implement a subscripting method within it. The subscripting method takes an Int parameter as the index and returns the value corresponding to the index. If the index is out of the range of the list, it returns nil.

Example 01:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
struct Matrix {
let rows: Int, columns: Int
var grid: [Double]
init(rows: Int, columns: Int) {
self.rows = rows
self.columns = columns
grid = Array(repeating: 0.0, count: rows * columns)
}
subscript(row: Int, column: Int) -> Double {
get {
return grid[(row * columns) + column]
}
set {
grid[(row * columns) + column] = newValue
}
}
}

In this example, a structure called Matrix is defined, which has a subscript that accepts two parameters of type Int. This subscript returns a value of type Double and is readable and writable.

Example 02:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
struct Vector3D {
var x = 0.0, y = 0.0, z = 0.0
subscript(index: Int) -> Double {
get {
switch index {
case 0:
return x
case 1:
return y
case 2:
return z
default:
fatalError("Invalid index")
}
}
set {
switch index {
case 0:
x = newValue
case 1:
y = newValue
case 2:
z = newValue
default:
fatalError("Invalid index")
}
}
}
}

var v = Vector3D()
v[0] = 1.0
v[1] = 2.0
v[2] = 3.0
print(v[0]) // Output "1.0"
print(v[1]) // Output "2.0"
print(v[2]) // Output "3.0"

In this example, a structure named Vector3D is defined and a subscript is defined that accepts a parameter of type Int. This subscript returns a value of type Double and is readable and writable. Then, an instance v of Vector3D is created, and subscripts are used to get and set the properties of v.

Customizing subscripting allows your type to support subscript syntax similar to arrays or dictionaries, making it more convenient to access and manipulate elements in custom types.