우리가 보는 대부분의 변수는 기본 데이터 유형이지만. 이러한 기본 데이터 유형은 대부분의 작업에 충분하지만 이것이 전부는 아닙니다.
기본 데이터 유형의 변수에도 제한이 있습니다.
- 기본 데이터 유형의 변수는 본질적으로 스칼라입니다. 이는 기본 데이터 유형의 각 변수가 한 번에 하나의 값만 저장할 수 있음을 의미합니다. 따라서 여러 값을 저장해야 할 경우 여러 변수를 반복적으로 정의해야 합니다. 예를 들어, a1, a2, a3... 수백, 수천 개의 값을 저장하고 싶다면 변수를 반복적으로 정의하는 이 방법은 작동하지 않습니다.
- 기본 데이터 유형의 변수 값이 메모리에서 위치하는 위치는 무작위입니다. 순차적으로 정의된 여러 변수의 경우 메모리의 저장 위치가 반드시 연속적인 것은 아닙니다. 따라서 변수가 선언된 순서대로 변수의 값을 얻을 수 있습니다.
배열은 일련의 데이터를 저장하는 데 사용되지만 동일한 유형의 일련의 변수로 간주되는 경우가 많습니다. 즉, 배열은 고정된 크기를 저장할 수 있는 동일한 유형의 요소를 순차적으로 모아 놓은 것입니다. .
배열의 선언은 숫자0, 숫자1,..., 숫자99 등의 개별 변수를 선언하는 것이 아니라, 숫자 등의 배열변수를 선언한 후 숫자[0], 숫자[1],... ., 숫자[99] 는 개별 변수를 나타냅니다. 배열의 특정 요소는 인덱스로 액세스할 수 있습니다.
배열은 동일한 데이터 유형의 값 모음으로 이해될 수 있습니다.
13.1 배열의 속성
- 배열의 정의는 실제로 동일한 데이터 유형의 연속적인 메모리 블록을 할당하는 것입니다.
- 배열은 정적입니다. 이는 일단 정의되고 초기화되면 길이를 변경할 수 없음을 의미합니다.
- 배열의 요소는 동일한 데이터 유형을 가지며 각 요소는 데이터 유형 크기의 메모리 블록을 차지합니다. 즉, 배열의 메모리 크기는 배열의 길이에 배열의 데이터 유형을 곱한 것과 같습니다.
- 배열의 각 요소는 순서대로 저장됩니다. 이 일련 번호는 요소의 저장 위치뿐만 아니라 배열 요소의 고유 식별자도 나타냅니다. 우리는 이 식별자를 배열 첨자라고 부릅니다. 배열 첨자는 0부터 시작한다는 점에 유의하세요.
- 배열의 각 요소를 채우는 과정을 배열 초기화 라고 합니다 . 즉, 배열 초기화는 배열의 각 요소에 값을 할당하는 것입니다.
- 배열 요소의 값은 업데이트하거나 수정할 수 있지만 배열 요소를 삭제할 수는 없습니다. 기능을 삭제하려는 경우 해당 값을 0 또는 삭제를 나타내는 다른 값에 할당할 수 있습니다.
13.2 배열 선언 및 초기화
Rust 언어는 배열 선언 및 초기화를 위한 3가지 구문을 제공합니다.
- 각 요소의 초기값을 지정하는 가장 기본적인 구문
- let variable_name:[dataType;size] = [value1,value2,value3];
예를 들어
- let arr:[i32;4] = [10,20,30,40];
- 배열 유형을 생략하는 구문
각 요소의 초기값이 명시되어 있으므로 초기값을 통해 배열의 타입을 유추할 수 있다.
- let variable_name = [value1,value2,value3];
예를 들어
- let arr = [10,20,30,40];
기본 초기화 값을 지정하기 위한 구문 - 이 구문을 기본값 초기화라고도 합니다.
각 요소에 대해 초기값을 지정하지 않으려면 모든 요소에 대해 기본 초기값을 지정할 수 있습니다.
- let variable_name:[dataType;size] = [default_value_for_elements,size];
예를 들어 다음 코드는 각 요소에 초기값 -1을 할당합니다.
- let arr:[i32;4] = [-1;4];
13.2.1 배열 초기화: 단순 배열
배열 초기화 구문은 일반적으로 다음과 같습니다.
- let variable_name = [value1,value2,value3];
이는 가장 기본적인 초기화 방법이자 가장 긴 초기화 방법으로, 배열의 유형을 명확하게 지정하는 것 외에도 각 배열 요소에 대한 초기값도 지정합니다.
배열은 복합 유형이므로 배열을 출력할 때 {:?} 형식 문자를 사용해야 합니다 .
Rust는 또한 요소의 형식인 배열의 길이를 반환하는 len() 메서드를 제공합니다.
- fn main(){
- let arr:[i32;4] = [10,20,30,40];
- println!("array is {:?}",arr);
- println!("array size is :{}",arr.len());
- }
위의 Rust 코드를 컴파일하고 실행하면 출력 결과는 다음과 같습니다.
- array is [10, 20, 30, 40]
- array size is :4
13.2.2 배열 초기화: 요소 데이터 유형 무시
배열 초기화 시 각 요소에 초기값을 지정하면 배열 정의 시 배열의 데이터 유형을 무시할 수 있습니다.
왜냐하면 이때 컴파일러는 요소의 데이터 유형을 통해 배열의 데이터 유형을 자동으로 유추할 수 있기 때문입니다.
예를 들어, 다음 코드에서 배열 길이는 4입니다. 왜냐하면 초기화 시 4개 요소의 초기 값이 정수로 지정되므로 배열 변수를 선언할 때 배열의 데이터 유형을 무시할 수 있기 때문입니다.
배열의 len() 함수는 배열의 길이를 반환하는 데 사용됩니다.
- fn main(){
- let arr = [10,20,30,40];
- println!("array is {:?}",arr);
- println!("array size is :{}",arr.len());
- }
위의 Rust 예제를 컴파일하고 실행하면 출력 결과는 다음과 같습니다.
- array is [10, 20, 30, 40]
- array size is :4
13.3 배열 기본값
배열을 초기화할 때 배열의 각 요소에 대한 값을 지정하지 않으려면 배열의 기본값을 설정할 수 있습니다. 즉, 기본값 초기화 구문을 사용할 수 있습니다.
기본값 초기화 구문을 사용하여 배열을 초기화하면 배열의 각 요소가 기본값으로 설정됩니다.
예를 들어 다음 코드에서는 배열의 모든 요소 값을 -1로 초기화합니다.
- fn main() {
- let arr:[i32;4] = [-1;4];
- println!("array is {:?}",arr);
- println!("array size is :{}",arr.len());
- }
위의 Rust 코드를 컴파일하고 실행하면 출력 결과는 다음과 같습니다.
- array is [-1, -1, -1, -1]
- array size is :4
13.4 배열 길이 len()
Rust는 배열의 길이를 반환하기 위해 배열에 len() 메서드를 제공합니다.
len() 메서드의 반환 값은 정수입니다.
예를 들어, 다음 코드에서는 len()을 사용하여 배열의 길이를 찾습니다.
- fn main() {
- let arr:[i32;4] = [-1;4];
- println!("array size is :{}",arr.len());
- }
위의 Rust 코드를 컴파일하고 실행하면 출력 결과는 다음과 같습니다.
- array size is :4
13.5 배열을 통한 for in 루프
다른 언어에서는 일반적으로 for 루프를 사용하여 배열을 순회하며 Rust 언어도 사용할 수 있지만 for 문의 변형인 for ... in .. 문이 사용됩니다.
배열의 길이는 컴파일 타임에 알려지기 때문에 for ... in 문을 사용하여 배열을 반복할 수 있습니다.
for in 구문에서 왼쪽으로 닫히는 규칙과 오른쪽으로 열리는 규칙에 주의하세요.
- fn main(){
- let arr:[i32;4] = [10,20,30,40];
- println!("array is {:?}",arr);
- println!("array size is :{}",arr.len());
-
- for index in 0..4 {
- println!("index is: {} & value is : {}",index,arr[index]);
- }
- }
위의 Rust 코드를 컴파일하고 실행하면 출력 결과는 다음과 같습니다.
- array is [10, 20, 30, 40]
- array size is :4
- index is: 0 & value is : 10
- index is: 1 & value is : 20
- index is: 2 & value is : 30
- index is: 3 & value is : 40
13.6 배열 iter() 반복
iter() 함수를 사용하여 배열에 대한 반복자를 생성할 수 있습니다.
그런 다음 for in 구문을 사용하여 배열을 반복할 수 있습니다.
- fn main(){
-
- let arr:[i32;4] = [10,20,30,40];
- println!("array is {:?}",arr);
- println!("array size is :{}",arr.len());
-
- for val in arr.iter(){
- println!("value is :{}",val);
- }
- }
위의 Rust 코드를 컴파일하고 실행하면 출력 결과는 다음과 같습니다.
- array is [10, 20, 30, 40]
- array size is :4
- value is :10
- value is :20
- value is :30
- value is :40
13.7 가변 배열
let을 사용하여 선언된 변수는 기본적으로 읽기 전용이며 배열도 예외는 아닙니다. 즉, 배열은 기본적으로 변경할 수 없습니다.
- fn main(){
- let arr:[i32;4] = [10,20,30,40];
- arr[1] = 0;
- println!("{:?}",arr);
- }
위의 코드는 실행 시 오류가 발생합니다. 오류 메시지는 다음과 같습니다.
- error[E0594]: cannot assign to `arr[_]`, as `arr` is not declared as mutable
- --> src/main.rs:3:4
- |
- 2 | let arr:[i32;4] = [10,20,30,40];
- | --- help: consider changing this to be mutable: `mut arr`
- 3 | arr[1] = 0;
- | ^^^^^^^^^^ cannot assign
-
- error: aborting due to previous error
배열의 불변성은 두 가지 형태로 나타납니다. 변수를 다른 배열에 다시 할당할 수 없고 배열 요소를 수정할 수 없습니다.
배열의 요소를 수정하려면 mut 키워드를 추가해야 합니다. 예를 들어
- let mut arr:[i32;4] = [10,20,30,40];
지금은 잘못된 코드를 수정해 보겠습니다
- fn main(){
- let mut arr:[i32;4] = [10,20,30,40];
- arr[1] = 0;
- println!("{:?}",arr);
- }
정상적으로 실행될 수 있으며 출력 결과는 다음과 같습니다.
- [10, 0, 30, 40]
13.8 함수 매개변수로서의 배열
배열은 함수의 매개변수로 사용될 수 있습니다. 전달 방법에는 값에 의한 전달 과 참조에 의한 전달이라는 두 가지 전송 방법이 있습니다 .
값으로 전달한다는 것은 배열 복사본을 매개변수로 함수에 전달하는 것을 의미합니다.
참조로 전달하는 것은 메모리의 배열 위치를 함수에 매개변수로 전달하는 것이므로 함수에 의한 배열 수정은 원래 배열에 영향을 미칩니다.
13.8.1 예제 1: 값으로 전달
다음 코드에서는 값별 전달 방법을 사용하여 배열을 함수에 매개변수로 전달합니다. 함수에 의한 매개변수 수정은 원래 배열에 영향을 주지 않습니다.
- fn main() {
- let arr = [10,20,30];
- update(arr);
-
- println!("Inside main {:?}",arr);
- }
- fn update(mut arr:[i32;3]){
- for i in 0..3 {
- arr[i] = 0;
- }
- println!("Inside update {:?}",arr);
- }
위의 Rust 코드를 컴파일하고 실행하면 출력 결과는 다음과 같습니다.
- Inside update [0, 0, 0]
- Inside main [10, 20, 30]
13.8.2 예제 2: 참조로 전달
다음 코드에서는 참조 메서드를 사용하여 배열을 매개변수로 함수에 전달합니다. 함수에 의한 매개변수 수정은 원래 배열에 영향을 미칩니다.
- fn main() {
- let mut arr = [10,20,30];
- update(&mut arr);
- println!("Inside main {:?}",arr);
- }
- fn update(arr:&mut [i32;3]){
- for i in 0..3 {
- arr[i] = 0;
- }
- println!("Inside update {:?}",arr);
- }
위의 Rust 코드를 컴파일하고 실행하면 출력 결과는 다음과 같습니다.
- Inside update [0, 0, 0]
- Inside main [0, 0, 0]
13.9 배열 선언과 상수
배열의 유일한 약점은 길이가 고정되어 컴파일 타임에 알려져야 한다는 것입니다.
배열을 선언할 때 길이는 정수 리터럴 또는 정수 상수로 지정되어야 합니다.
배열 길이가 변수인 경우 컴파일 오류가 보고됩니다. 예를 들어 다음 코드는
- fn main() {
- let N: usize = 20;
- let arr = [0; N]; //오류: 상수와 함께 사용된 비상수
- print!("{}",arr[10])
- }
위의 Rust 코드를 컴파일하면 오류가 보고됩니다.
- error[E0435]: attempt to use a non-constant value in a constant
- --> main.rs:3:18
- |
- 3 | let arr = [0; N]; //오류: 상수와 함께 사용된 비상수
- | ^ non-constant value
-
- error: aborting due to previous error
-
- For more information about this error, try `rustc --explain E0435`.
오류 이유는 다음과 같습니다. N은 상수가 아닙니다.
N은 기본적으로 읽기 전용이지만 여전히 변수이며 읽기 전용 변수는 상수가 아닙니다. 변수의 값은 런타임에 결정되는 반면 상수의 값은 컴파일러에 의해 결정되기 때문입니다.
변수는 배열의 길이로 사용될 수 없습니다.
let 키워드를 const 키워드로 변경하면 컴파일이 통과됩니다.
- fn main() {
- const N: usize = 20;
- //고정된 크기
- let arr = [0; N];
-
- print!("{}",arr[10])
- }
위의 Rust 코드를 컴파일하고 실행하면 출력 결과는 다음과 같습니다.
- 0
usize는 포인터가 차지하는 크기입니다. 실제 크기는 프로그램을 컴파일한 CPU 아키텍처에 따라 다릅니다.
현재 콘텐츠 저작권은 chapin666 또는 그 계열사에 있습니다.