1
- ## Variables and Mutability
1
+ ## 변수와 가변성
2
2
3
- As mentioned in Chapter 2, by default variables are * immutable* . This is one of
4
- many nudges in Rust that encourages you to write your code in a way that takes
5
- advantage of the safety and easy concurrency that Rust offers. However, you
6
- still have the option to make your variables mutable. Let’s explore how and why
7
- Rust encourages you to favor immutability, and why you might want to opt out.
3
+ 2 장에서 언급했듯이, 기본 변수는 * 불변성* 입니다. 이것은 Rust가 제공하는 안전성과 손쉬운 동시성이라는 장점을
4
+ 취할 수 있도록 코드를 작성하게끔 강제하는 요소 중 하나 입니다. 하지만 여전히 당신은 가변 변수를 사용하고 싶을테죠.
5
+ 어떻게 그리고 왜 Rust에서 불변성을 애호해주길 권장하는지 알아보면 그런 생각을 포기할 수 있을지도 모르겠습니다.
8
6
9
- When a variable is immutable, that means once a value is bound to a name, you
10
- can’t change that value. To illustrate, let’s generate a new project called
11
- * variables* in your * projects* directory by using ` cargo new --bin variables ` .
12
-
13
- Then, in your new * variables* directory, open * src/main.rs* and replace its
14
- code with the following:
7
+ 변수가 불변성인 경우, 일단 값이 이름에 bound되면 해당 값을 변경할 수 없습니다. 시험 삼아
8
+ ` cargo new --bin variables ` 을 실행해서 * projects * 디렉토리에 * variables * 라는 새 프로젝트를
9
+ 생성 해 봅시다. 그런 다음 새 * variables * 디렉토리에서 * src / main.rs * 를 열고 코드를 다음과 같이
10
+ 바꿉니다.
15
11
16
12
<span class =" filename " >Filename: src/main.rs</span >
17
13
@@ -24,8 +20,7 @@ fn main() {
24
20
}
25
21
```
26
22
27
- Save and run the program using ` cargo run ` . You should receive an error
28
- message, as shown in this output:
23
+ 저장하고 ` cargo run ` 명령을 통해 실행시켜 봅시다. 당신은 다음과 같이 출력되는 에러를 확인하게 될 겁니다.
29
24
30
25
``` text
31
26
error[E0384]: re-assignment of immutable variable `x`
@@ -38,34 +33,26 @@ error[E0384]: re-assignment of immutable variable `x`
38
33
| ^^^^^ re-assignment of immutable variable
39
34
```
40
35
41
- This example shows how the compiler helps you find errors in your programs.
42
- Even though compiler errors can be frustrating, they only mean your program
43
- isn’t safely doing what you want it to do yet; they do * not* mean that you’re
44
- not a good programmer! Experienced Rustaceans still get compiler errors. The
45
- error indicates that the cause of the error is `re-assignment of immutable
46
- variable` , because we tried to assign a second value to the immutable ` x`
47
- variable.
48
-
49
- It’s important that we get compile-time errors when we attempt to change a
50
- value that we previously designated as immutable because this very situation
51
- can lead to bugs. If one part of our code operates on the assumption that a
52
- value will never change and another part of our code changes that value, it’s
53
- possible that the first part of the code won’t do what it was designed to do.
54
- This cause of bugs can be difficult to track down after the fact, especially
55
- when the second piece of code changes the value only * sometimes* .
56
-
57
- In Rust the compiler guarantees that when we state that a value won’t change,
58
- it really won’t change. That means that when you’re reading and writing code,
59
- you don’t have to keep track of how and where a value might change, which can
60
- make code easier to reason about.
61
-
62
- But mutability can be very useful. Variables are immutable only by default; we
63
- can make them mutable by adding ` mut ` in front of the variable name. In
64
- addition to allowing this value to change, it conveys intent to future readers
65
- of the code by indicating that other parts of the code will be changing this
66
- variable value.
67
-
68
- For example, change * src/main.rs* to the following:
36
+ 위의 예제는 컴파일러가 당신이 만든 프로그램에서 당신을 도와 에러를 찾아주는 방법에 대해 보여주고 있습니다.
37
+ 컴파일러 에러가 힘빠지게 만들 수도 있지만, 단지 당신의 프로그램이 아직 안전하게 수행되긴 미흡하다는 뜻이지,
38
+ 당신의 소양이 부족함을 의미하는건 아닙니다. 숙련된 Rustacean들도 여전히 에러를 발생시키니까요. 에러가
39
+ 나타내는 것은 ` 불변성 변수에 재할당 ` 이고, 원인은 우리가 불변성 변수 ` x ` 에 두 번째로 값을 할당했기 때문입니다.
40
+
41
+ 우리가 이전에 불변성으로 선언한 것의 값을 변경하고자 하는 시도를 하면 컴파일 타임의 에러를 얻게 되고 이로 인해
42
+ 버그가 발생할 수 있기 때문에 중요합니다. 만약 우리 코드의 일부는 값이 변경되지 않는다는 것을 가정하는데 다른 코드는
43
+ 이와 다르게 값을 변경한다면, 전자에 해당하는 코드는 우리가 의도한 대로 수행되지 않을 수 있습니다. 특히 후자에
44
+ 해당되는 코드가 항상 그렇지 않고 * 가끔* 값을 변경하는 경우 나중에 버그의 원인을 추적하기가 매우 어렵습니다.
45
+
46
+ Rust에서는 컴파일러가 변경되지 않은 값에 대한 보증을 해주고, 실제로 이는 바뀌지 않습니다. 이것이 의미하는
47
+ 바는 당신이 코드를 작성하거나 분석할 시에 변수의 값이 어떻게 변경되는지 추적할 필요가 없기 때문에 코드를 더
48
+ 합리적으로 만들어줍니다.
49
+
50
+ 하지만 가변성은 매우 유용하게 사용될 수 있습니다. 변수는 기본적으로 불변성이지만 우리는 변수명의 접두어로
51
+ ` mut ` 을 추가하는 것을 통해 가변성 변수를 선언할 수 있습니다. 이 변수의 값이 변경을 허용하는 것에 추가로
52
+ 향후 코드를 보는 사람에게 코드의 다른 부분에서 해당 변수의 값을 변경할 것이라는 의도를 주지시킵니다.
53
+
54
+ 예를 들어, * src/main.rs* 를 다음과 같이 변경해보도록 합니다.
55
+
69
56
70
57
<span class =" filename " >Filename: src/main.rs</span >
71
58
@@ -78,7 +65,7 @@ fn main() {
78
65
}
79
66
```
80
67
81
- When we run this program, we get the following :
68
+ 위의 프로그램을 수행하면 다음과 같은 결과를 얻게 됩니다 :
82
69
83
70
``` text
84
71
$ cargo run
@@ -88,68 +75,55 @@ The value of x is: 5
88
75
The value of x is: 6
89
76
```
90
77
91
- Using ` mut ` , we’re allowed to change the value that ` x ` binds to from ` 5 ` to
92
- ` 6 ` . In some cases, you’ll want to make a variable mutable because it makes the
93
- code more convenient to write than an implementation that only uses immutable
94
- variables.
78
+ ` mut ` 를 사용하여, ` x ` 에 bind된 값을 ` 5 ` 에서 ` 6 ` 으로 변경할 수 있습니다. 불변성 변수만을 사용하는 것보다
79
+ 가변성 변수를 사용하여 보다 쉽게 구현할 수 있을 경우 가변성 변수를 만들어 사용할 수도 있습니다.
80
+
81
+ 이런 의사 결정에 있어서 버그를 예방하는 것 외에도 고려해야 할 요소들이 있습니다. 예를 들어, 대규모 데이터 구조체를
82
+ 다루는 경우 가변한 인스턴스를 사용하는 것이 새로 인스턴스를 할당하고 반환하는 것보다 빠를 수 있습니다. 데이터 규모가
83
+ 작을수록 새 인스턴스를 생성하고 함수적 프로그래밍 스타일로 작성하는 것이 더 합리적이고, 그렇기에 약간의 성능 하락을
84
+ 통해 가독성을 확보할 수 있다면 더 가치있는 선택입니다.
95
85
96
- There are multiple trade-offs to consider, in addition to the prevention of
97
- bugs. For example, in cases where you’re using large data structures, mutating
98
- an instance in place may be faster than copying and returning newly allocated
99
- instances. With smaller data structures, creating new instances and writing in
100
- a more functional programming style may be easier to reason about, so the lower
101
- performance might be a worthwhile penalty for gaining that clarity.
102
86
103
- ### Differences Between Variables and Constants
87
+ ### 변수와 상수 간의 차이점들
104
88
105
- Being unable to change the value of a variable might have reminded you of
106
- another programming concept that most other languages have: * constants* . Like
107
- immutable variables, constants are also values that are bound to a name and
108
- are not allowed to change, but there are a few differences between constants
109
- and variables.
89
+ 변수의 값을 변경할 수 없다는 사항이 아마 당신에게 다른 언어가 가진 프로그래밍 개념을 떠오르게 하지 않나요: * 상수*
90
+ 불변성 변수와 마찬가지로 상수 또한 이름으로 bound된 후에는 값의 변경이 허용되지 않지만, 상수와 변수는 조금
91
+ 다릅니다.
110
92
111
- First, we aren’t allowed to use ` mut ` with constants: constants aren't only
112
- immutable by default, they're always immutable .
93
+ 첫 째로, 상수에 대해서는 ` mut ` 을 사용하는 것이 허용되지 않습니다: 상수는 기본 설정이 불변성인 것이 아니고
94
+ 불변성 그 자체 입니다 .
113
95
114
- We declare constants using the ` const ` keyword instead of the ` let ` keyword,
115
- and the type of the value * must* be annotated. We're about to cover types and
116
- type annotations in the next section, “Data Types,” so don't worry about the
117
- details right now, just know that we must always annotate the type.
96
+ 우리가 상수를 사용하고자 하면 ` let ` 키워드 대신 ` const ` 키워드를 사용해야 하고, 값의 유형을 선언해야
97
+ 합니다. 우리가 사용할 수 있는 유형들과 유형의 선언을 챕터 “Data Types,”에서 다루게 될 것이므로 자세한
98
+ 사항은 지금 걱정하지 말고, 우리는 반드시 값의 유형을 선언해야 한다는 것을 알고 지나갑시다.
118
99
119
- Constants can be declared in any scope, including the global scope, which makes
120
- them useful for values that many parts of code need to know about .
100
+ 상수는 전체 영역을 포함하여 어떤 영역에서도 선언될 수 있습니다. 이는 코드의 많은 부분에서 사용될 필요가 있는
101
+ 값을 다루는데 유용합니다 .
121
102
122
- The last difference is that constants may only be set to a constant expression,
123
- not the result of a function call or any other value that could only be
124
- computed at runtime.
103
+ 마지막 차이점은 상수는 오직 상수 표현식만 설정될 수 있지, 함수 호출의 결과값이나 그 외에 실행 시간에 결정되는
104
+ 값이 설정될 수는 없다는 점 입니다.
125
105
126
- Here's an example of a constant declaration where the constant's name is
127
- ` MAX_POINTS ` and its value is set to 100,000. (Rust constant naming convention
128
- is to use all upper case with underscores between words):
106
+ 아래의 ` MAX_POINTS ` 라는 이름을 갖는 상수를 선언하는 예제에서는 값을 100,000으로 설정합니다. (Rust의
107
+ 상수 명명 규칙에 따라 모든 단어를 대문자로 사용합니다.)
129
108
130
109
``` rust
131
110
const MAX_POINTS : u32 = 100_000 ;
132
111
```
133
112
134
- Constants are valid for the entire time a program runs, within the scope they
135
- were declared in, making them a useful choice for values in your application
136
- domain that multiple parts of the program might need to know about, such as the
137
- maximum number of points any player of a game is allowed to earn or the speed
138
- of light.
113
+ 상수는 자신이 선언되어 있는 영역 내에서 프로그램이 실행되는 시간 동안 항상 유효하기에, 당신의 어플리케이션 도메인 전체에
114
+ 걸쳐 프로그램의 다양한 곳에서 사용되는 값을 상수로 하면 유용합니다. 사용자가 한 게임에서 획득할 수 있는 최대 포인트,
115
+ 빛의 속도 같은 값 등등...
139
116
140
- Naming hardcoded values used throughout your program as constants is useful in
141
- conveying the meaning of that value to future maintainers of the code. It also
142
- helps to have only one place in your code you would need to change if the
143
- hardcoded value needed to be updated in the future.
117
+ 당신의 프로그램 전체에 걸쳐 하드코드 해야 하는 값을 이름지어 상수로 사용하면 향후 코드를 유지보수 하게 될 사람에게
118
+ 그 의미를 전달할 수 있으므로 유용합니다. 또한 향후 해당 값을 변경해야 하는 경우에 상수로 선언된 값 한 곳만 변경하면
119
+ 되므로 도움이 될 겁니다.
144
120
145
121
### Shadowing
146
122
147
- As we saw in the guessing game tutorial in Chapter 2, we can declare a new
148
- variable with the same name as a previous variable, and the new variable
149
- * shadows* the previous variable. Rustaceans say that the first variable is
150
- * shadowed* by the second, which means that the second variable’s value is what
151
- we’ll see when we use the variable. We can shadow a variable by using the same
152
- variable’s name and repeating the use of the ` let ` keyword as follows:
123
+ 앞서 우리가 2장에서 추측 게임 예제를 통해 봤듯이, 이전에 선언한 변수와 같은 이름의 새 변수를 선언할 수 있고,
124
+ 새 변수는 이전 변수를 * shadows* 하게 됩니다. Rustaceans들은 이를 첫 변수가 두 번째에 의해 * shadowed*
125
+ 됐다고 표현하게 됩니다. 해당 변수명은 두 번째 변수의 값을 갖게 된다는 뜻이죠. ` let ` 키워드를 사용해서 다음처럼
126
+ 반복하여 같은 변수 명으로 변수를 shadow 할 수 있습니다.
153
127
154
128
<span class =" filename " >Filename: src/main.rs</span >
155
129
@@ -165,11 +139,9 @@ fn main() {
165
139
}
166
140
```
167
141
168
- This program first binds ` x ` to a value of ` 5 ` . Then it shadows ` x ` by
169
- repeating ` let x = ` , taking the original value and adding ` 1 ` so the value of
170
- ` x ` is then ` 6 ` . The third ` let ` statement also shadows ` x ` , taking the
171
- previous value and multiplying it by ` 2 ` to give ` x ` a final value of ` 12 ` .
172
- When you run this program, it will output the following:
142
+ 이 프로그램은 처음 ` x ` 에 값 ` 5 ` 를 bind 합니다. 이후 반복된 ` let x = ` 구문으로 ` x ` 를 shadow하고
143
+ 원본 값에 ` 1 ` 을 더해서 ` x ` 의 값은 ` 6 ` 이 됩니다. 세 번째 ` let ` 문으로 또 ` x ` 를 shadow하고, 이전
144
+ 값에 ` 2 ` 를 곱하여 ` x ` 의 최종값은 ` 12 ` 가 됩니다. 이 프로그램을 실행하면 다음과 같은 결과를 볼 수 있습니다.
173
145
174
146
``` text
175
147
$ cargo run
@@ -178,36 +150,32 @@ $ cargo run
178
150
The value of x is: 12
179
151
```
180
152
181
- This is different than marking a variable as ` mut ` , because unless we use the
182
- ` let ` keyword again, we’ll get a compile-time error if we accidentally try to
183
- reassign to this variable. We can perform a few transformations on a value but
184
- have the variable be immutable after those transformations have been completed.
153
+ 이와 같은 사용은 변수를 ` mut ` 으로 선언하는 것과는 차이가 있게 됩니다. 왜냐면 ` let ` 키워드를 사용하지 않고 변수에
154
+ 새로 값을 대입하려고 하면 컴파일-시에 에러를 얻게 되기 때문이죠. 우리가 몇 번 값을 변경할 수는 있지만 그 이후에
155
+ 변수는 불변성을 갖게 됩니다.
156
+
157
+ 또 다른 ` mut ` 과 shadowing의 차이는 ` let ` 키워드를 다시 사용하여 효과적으로 새 변수를 선언하고, 값의 유형을
158
+ 변경할 수 있으면서도 동일 이름을 사용할 수 있다는 점 입니다. 예를 들어, 공백 문자들을 입력받아 얼마나 많은 공백
159
+ 문자가 있는지 보여주고자 할 때, 실제로는 저장하고자 하는 것은 공백의 갯수일테죠.
185
160
186
- The other difference between ` mut ` and shadowing is that because we’re
187
- effectively creating a new variable when we use the ` let ` keyword again, we can
188
- change the type of the value, but reuse the same name. For example, say our
189
- program asks a user to show how many spaces they want between some text by
190
- inputting space characters, but we really want to store that input as a number:
191
161
192
162
``` rust
193
163
let spaces = " " ;
194
164
let spaces = spaces . len ();
195
165
```
196
166
197
- This construct is allowed because the first ` spaces ` variable is a string type,
198
- and the second ` spaces ` variable, which is a brand-new variable that happens to
199
- have the same name as the first one, is a number type. Shadowing thus spares us
200
- from having to come up with different names, like ` spaces_str ` and
201
- ` spaces_num ` ; instead, we can reuse the simpler ` spaces ` name. However, if we
202
- try to use ` mut ` for this, as shown here:
167
+ 이와 같은 구조가 허용되는 이유는 첫 ` spaces ` 변수가 문자열 유형이고 두 번째 ` spaces ` 변수는 첫 번째 것과
168
+ 동일한 이름을 가진 새롭게 정의된 숫자 유형의 변수이기 때문입니다. Shadowing은 ` space_str ` 이나 ` space_num `
169
+ 과 같이 대체된 이름을 사용는 대신 간단히 ` spaces ` 이름을 사용할 수 있게 해줍니다. 그러나 우리가 ` mut ` 을 사용하려고
170
+ 했다면:
203
171
204
172
``` rust,ignore
205
173
let mut spaces = " ";
206
174
spaces = spaces.len();
207
175
```
208
176
209
- we’ll get a compile-time error because we’re not allowed to mutate a variable’s
210
- type:
177
+ 우리는 다음처럼 변수의 유형을 변경할 수 없다는 컴파일-시의 에러를 얻게 될 겁니다:
178
+
211
179
212
180
``` text
213
181
error[E0308]: mismatched types
@@ -220,5 +188,4 @@ error[E0308]: mismatched types
220
188
found type `usize`
221
189
```
222
190
223
- Now that we’ve explored how variables work, let’s look at more data types they
224
- can have.
191
+ 변수가 어떻게 동작하는지 탐구했으니, 더 많은 데이터 유형을 사용 살펴보도록 합시다.
0 commit comments