상위 문서: 색인 표현식   [차례][찾아보기]


8.1.1 고급 색인

색인을 요소의 곱집합으로 나타낼 수 없는 배열의 어귀에서 부분 집합을 뽑아내야 하면, 선형 색인을 sub2ind와 사용하면 됩니다. 예시:

A = reshape (1:8, 2, 2, 2)  # 3차원 배열 만들기
A =

ans(:,:,1) =

   1   3
   2   4

ans(:,:,2) =

   5   7
   6   8

A(sub2ind (size (A), [1, 2, 1], [1, 1, 2], [1, 2, 1]))
   ⇒ ans = [A(1, 1, 1), A(2, 1, 2), A(1, 2, 1)]

nd’ 차원인 배열은 1 개에서 ‘nd’ 개까지의 요소를 가진 색인 표현식으로 색인합니다. 일반적이고, 가장 많은 경우는 색인 요소 개수 ‘M’이 차원 개수 ‘nd’와 같은 것입니다. 이 경우는 일반적인 색인 규칙이 적용되어 각 색인 요소가 각 배열의 차원에 맞물립니다.

그러나 색인 요소 개수가 차원 개수보다 많으면(M > nd), 초과한 색인 요소는 모두 단일(1)이 됩니다. 더욱이 M < nd이면 입력 객체의 모양을 고치는 방법이 같아, 남은 nd - M 차원을 마지막 색인 차원 M과 결부합니다. 그러므로 결과는 본래 객체의 차원수가 아닌 색인 표현식의 차원수를 가집니다. 색인 차원수가 1보다 크기만하면(M > 1) 이런 방식이며, 선형 색인용 특별 규칙을 적용하지 않습니다. 예시를 보면 쉽게 이해할 수 있습니다.

A = reshape (1:8, 2, 2, 2)  # 3차원 배열 만들기
A =

ans(:,:,1) =

   1   3
   2   4

ans(:,:,2) =

   5   7
   6   8

## 세 번째 차원이 두 번째 차원에 결부하기에 2차원 색인을 합니다.
## 색인에 동등한 배열인  Atmp이 2x4가 됨.
Atmp = reshape (A, 2, 4)
Atmp =

   1   3   5   7
   2   4   6   8


A(2,1)   # 2x4 행렬로 고쳐, 첫 번째 열의 두 번째 어귀: ans = 2
A(2,4)   # 2x4 행렬로 고쳐, 네 번째 열의 두 번째 어귀: ans = 8
A(:,:)   # 2x4 행렬로 고쳐, 모든 행과 열 선택: ans = Atmp

reshape 함수 호출을 대신하는 멋진 방법으로 쌍점 두 개가 있습니다.

선형 색인의 고급 사용법으로 배열을 만들어 단일 값으로 채우는 것도 있습니다. ones 색인에 스칼라 값을 딸려주는 방식입니다. 색인 표현식의 차원 크기인 객체의 원소가 모두 딸린 스칼라입니다. 예를 들어, 아래 명령문은

a = 13;
a(ones (1, 4))

원소 네 개가 모두 13인 행 벡터를 만듭니다.

비슷하게 ones인 벡터 두 개를 색인하여 행렬을 만들기도 합니다. 아래 명령문은

a = 13;
a(ones (1, 2), ones (1, 3))

모든 원소가 13인 2x3짜리 행렬을 만듭니다. 이는 아래아 같이 적어도 됩니다.

13(ones (2, 3))

색인으로 행렬을 만들면 불필요한 곱셈을 하지 않기 때문에 scalar * ones (M, N, …)보다 효율적입니다. 더욱이 배열 색인은 언제나 정의되어 있는데 반하여, 객체 복제를 위한 곱셈은 정의되어 있지 않을 수 있습니다. 아래 부호는 자기 자신은 스칼라가 아닌 단위로 2x3짜리 낱칸 배열을 만드는 방법을 보여줍니다.

{"Hello"}(ones (2, 3))

ones (1, n)(ones의 행 벡터)가 범위 객체(증감 0)를 도출한다는 점에 꼭 유의하여야 합니다. 범위는 내부에서 시작값, 증감도, 끝값, 값의 총 개수로 저장합니다. 그렇기에 원소 개수가 4 개를 넘으면, 벡터나 행렬로 저장하는 것보다 범위로 저장하는 것이 더 효율적입니다.

  r(ones (1, n), :)
  r(ones (n, 1), :)

위 명령문은 같은 결과를 내지만, ‘r’과 ‘n’이 충분하게 크면 첫 번째 용례가 확연하게 빠릅니다. 첫 번째 용례는 범위를 사용하여 옥타브가 표현식을 다루는데에 더 효과적인 셈법인 압축 형식을 활용합니다.

이런 요령에 익숙하지 않은 사용자에게 가장 추천하는 방법은 비슷한 역할을 하는 함수 repmat을 큰 배열에 작은 배열을 복제하여 넣는데에 사용하는 것입니다.

색인의 두 번째 사용법이 부호 속도를 높히는 것입니다. 색인은 빠른 연산자이며, 색인의 적절한 활용은 처리 속도를 느리게 하는 개별 배열 원소를 반복 처리의 필요를 줄여줍니다.

값이 a(i) = sqrt (i)인 원소 10개 짜리 행 벡터 a를 만드는 방식으로 아래 예시를 주의하여 보십시오.

for i = 1:10
  a(i) = sqrt (i);
endfor

이런 식으로 반복하여 벡터를 만드는 것은 꽤나 비효율적입니다. 이 행 벡터는 아래 표현식으로 더 효율적으로 만듭니다.

a = sqrt (1:10);

반복을 전혀 쓰지 않습니다.

반복을 사용하여야 하거나 많은 값을 큰 행렬에 집어 넣어야 하는 경우, 먼저 필요한 크기의 행렬을 설정하고(미리 할당한 저장소) 난 다음에 색인 명령을 사용하여 원소를 끼워 넣는 것이 보통 빠릅니다. 예를 들어, 행렬 a가 주어지면,

[nr, nc] = size (a);
x = zeros (nr, n * nc);
for i = 1:n
  x(:,(i-1)*nc+1:i*nc) = a;
endfor

아래보다 위가 더 상당히 빠릅니다.

x = a;
for i = 1:n-1
  x = [x, a];
endfor

왜냐하면 옥타브는 중간 결과의 크기를 반복적으로 조정하지 않기 때문입니다.

형_색인 = sub2ind (차원, i, j)
형_색인 = sub2ind (차원, s1, s2, …, sN)

안긴 내용을 선형 색인으로 바꿉니다.

입력 차원은 각 원소가 배열의 특정 차원 크기인 차원 벡터입니다.(크기 참조) 나머지 입력은 변환할 안긴 스칼라 또는 벡터입니다.

출력 벡터 선형_색인에 변환한 선형 색인을 담습니다.

뒷면: 배열 원소를 1로 시작하는 선형 색인으로 지정하여 배열 내 원소 개수만큼 실행하거나, 안긴 내용를 얻기 위하여 행·열·면 등을 지정합니다. 함수 ind2subsub2ind가 이 두 형태를 왔다갔다 합니다.

선형 색인이 차원1(행), 차원2(열), 차원3(면) 등을 원소를 모두 읽을 때까지 종단합니다.. 아래 3×3 행렬을 생각하여 봅시다.

[(1,1), (1,2), (1,3)]     [1, 4, 7]
[(2,1), (2,2), (2,3)] ==> [2, 5, 8]
[(3,1), (3,2), (3,3)]     [3, 6, 9]

왼쪽 행렬은 각 행렬 원소에 대한 안긴 속성 집합을 가집니다. 오른쪽 행렬은 같은 행렬에서의 선형 색인을 보여줍니다.

아래 예시는 3×3 행렬에서의 2차원 색인 (2,1)(2,3)을 한 번의 sub2ind호출로 선형 색인으로 바꾸는 방법을 보여줍니다.

s1 = [2, 2];
s2 = [1, 3];
ind = sub2ind ([3, 3], s1, s2)
    ⇒ ind =  2   8

같이 보기: ind2sub, size.

[s1, s2, …, sN] = ind2sub (차원, 선형_색인)

선형 색인을 안긴 내용으로 바꿉니다.

입력 차원은 각 원소가 배열의 개별 차원의 크기인 차원 벡터입니다.(크기 참조) 두 번째 입력 선형_색인은 바꿀 선형 색인입니다.

출력 s1, …, sN은 바꾼 안긴 내용을 담습니다.

뒷면: 배열 원소를 1로 시작하는 선형 색인으로 지정하여 배열 내 원소 개수만큼 실행하거나, 안긴 내용를 얻기 위하여 행·열·면 등을 지정합니다. 함수 ind2subsub2ind가 이 두 형태를 왔다갔다 합니다.

선형 색인이 차원1(행), 차원2(열), 차원3(면) 등을 원소를 모두 읽을 때까지 종단합니다.. 아래 3×3 행렬을 생각하여 봅시다.

[1, 4, 7]     [(1,1), (1,2), (1,3)]
[2, 5, 8] ==> [(2,1), (2,2), (2,3)]
[3, 6, 9]     [(3,1), (3,2), (3,3)]

왼쪽 행렬은 각 행렬 원소에 대한 선형 색을 가집니다. 오른쪽 행렬은 같은 행렬에서의 안긴 속성 집합을 보여줍니다.

아래 예시는 3×3 행렬에서의 2차원 색인 (2,1)(2,3)을 한 번의 sub2ind호출로 선형 색인으로 바꾸는 방법을 보여줍니다.

T아래 예시는 3×3 행렬에서의 선형 색인 28을 안긴 내용으로 바꾸는 방법을 보여줍니다.

ind = [2, 8];
[r, c] = ind2sub ([3, 3], ind)
    ⇒ r =  2   2
    ⇒ c =  1   3

출력 안긴 내용의 개수가 차원 개수를 넘어가면, 초과하는 차원은 모두 1이 됩니다. 다른 말로 하자면, 차원보다 작은 안긴 내용을 주면, 초과하는 차원은 마지막으로 요청한 차원과 합쳐집니다. 명확하게 알려면, 아래 예시를 보십시오.

ind  = [2, 8];
dims = [3, 3];
## dims = [3, 3, 1]와 같음
[r, c, s] = ind2sub (dims, ind)
    ⇒ r =  2   2
    ⇒ c =  1   3
    ⇒ s =  1   1
## dims = [9]와 같음
r = ind2sub (dims, ind)
    ⇒ r =  2   8

같이 보기: ind2sub, size.

isindex (선형_색인)
isindex (선형_색인, n)

선형_색인이 올바른 색인이면, 참을 반환합니다.

올바른 색인은 양의 정수(실수 자료형도 가능) 또는 논리 배열입니다.

n은 존재하는 경우에 색인할 최대 차원 범위를 정합니다. 내부 결과를 시렁에 저장할 수 있는 경우에는 선형_색인을 사용하는 다음 색인에서는 n을 확인하지 않습니다.

실행 안내: 올바른 색인인지 확인하기 전에 문자열이 배정도 값으로 먼저 바뀝니다. 문자열이 빈 문자 "\0"를 가지지 않는 한 언제나 올바른 색인입니다.


상위 문서: 색인 표현식   [차례][찾아보기]