배열 프로그래밍

Array programming

컴퓨터 과학에서 어레이 프로그래밍은 연산 전체를 한 번에 적용할 수 있는 솔루션을 말합니다.이러한 솔루션은 과학 및 엔지니어링 환경에서 일반적으로 사용됩니다.

어레이 프로그래밍을 지원하는 최신 프로그래밍 언어(벡터 또는 다차원 언어라고도 함)는 벡터, 매트릭스 및 고차원 배열에 투명하게 적용하기 위해 스칼라 연산을 일반화하도록 특별히 설계되었습니다.여기에는 APL, J, Fortran 90, MATLAB, Analytica, TK 솔버(목록), Octabe, R, Cilk Plus, Julia, Perl Data Language(PDL) 등포함됩니다.이들 언어에서 어레이 전체에서 동작하는 연산은 벡터 명령을 구현하는 벡터 프로세서에서 실행되는지 여부에 관계없이 벡터화[1]연산이라고 할 수 있습니다.어레이 프로그래밍 프리미티브는 데이터 조작에 관한 폭넓은 아이디어를 간결하게 표현합니다.콘시젼의 레벨은 경우에 따라서는 극단적일 수 있습니다.여러 페이지의 객체 지향 코드를 필요로 하는 어레이 프로그래밍 언어의 1행은 드물지 않습니다[example needed].

어레이의 개념

어레이 프로그래밍의 기본 개념은 연산이 전체 값 집합에 동시에 적용된다는 것입니다.를 통해 프로그래머는 개별 스칼라 연산의 명시적 루프에 의존하지 않고 전체 데이터 집합에서 사고 및 연산을 수행할 수 있기 때문에 고급 프로그래밍 모델이 됩니다.

케네스 E. Iverson은 어레이 프로그래밍(실제로는 APL)의 이면에 있는 이유를 다음과 같이 [2]설명했습니다.

대부분의 프로그래밍 언어는 수학 표기법보다 확실히 열등하며 응용 수학자에 의해 중요하게 여겨질 수 있는 사고 도구로서 거의 사용되지 않는다.

그 명제는 프로그래밍 언어에서 발견되는 실행 가능성과 보편성의 장점이 하나의 일관된 언어로 수학적 표기법에 의해 제공되는 이점과 효과적으로 결합될 수 있다는 것이다.표기법의 기술 및 학습의 어려움과 그 의미를 이해하는 것의 어려움을 구별하는 것은 중요하다.예를 들어 행렬 곱을 계산하는 규칙을 배우는 것은 쉽지만, 그 의미(연관성, 덧셈에 대한 분포, 선형함수와 기하학적 연산을 나타내는 능력 등)에 대한 숙달은 훨씬 더 어렵고 다른 문제이다.

실제로, 표기의 매우 암시적인 것은 그것이 탐구를 위해 제안하는 많은 특성 때문에 배우는 것을 어렵게 할 수 있다.

[...]

컴퓨터 및 프로그래밍 언어 사용자는 주로 알고리즘 실행의 효율성에 관심을 가지기 때문에 여기에 제시된 알고리즘의 많은 부분을 간단히 무시할 수 있습니다.알고리즘의 명확한 스테이트먼트가 보다 효율적인 알고리즘을 쉽게 도출할 수 있는 기준으로 사용될 수 있기 때문에 이러한 해고는 근시안적일 수 있습니다.

어레이 프로그래밍과 사고의 기본은 개별 요소가 비슷하거나 인접한 데이터의 속성을 찾아 활용하는 것입니다.데이터를 구성 요소(또는 스칼라 수)로 암묵적으로 분해하는 객체 방향과 달리 어레이 방향은 데이터를 그룹화하고 균일한 처리를 적용합니다.

함수 순위는 일반적으로 수학의 텐서 순위와 유사하게 프로그래밍 언어를 배열하는 데 중요한 개념입니다. 데이터에 대해 작동하는 함수는 해당 함수가 작용하는 차원의 수에 따라 분류될 수 있습니다.예를 들어, 일반 곱셈은 0차원 데이터(개별 번호)에서 작동하기 때문에 스칼라 순위 함수입니다.교차곱 연산은 스칼라가 아닌 벡터로 작동하기 때문에 벡터 순위 함수의 한 예입니다.행렬 곱셈은 2차원 객체(매트릭스)에서 작동하기 때문에 2-랭크 함수의 한 예입니다.축소 연산자는 입력 데이터 배열의 치수를 하나 이상 축소합니다.예를 들어 요소를 합산하면 입력 배열이 1차원 축소됩니다.

사용하다

어레이 프로그래밍은 암묵적 병렬화에 매우 적합하며, 오늘날 많은 연구가 이루어지고 있는 주제입니다.또한 1997년 이후에 개발 및 생산된 인텔 및 호환 CPU에는 기본적인 SIMD 어레이 기능을 포함한 MMX에서 SSE3 및 3DNow!까지 다양한 명령어 세트 확장이 포함되어 있습니다.어레이 처리는 1개의 물리 프로세서가 아이템 그룹에 대해 동시에 조작을 실행한다는 점에서 병렬 처리와 구별됩니다.병렬 처리는 큰 문제를 작은 문제로 분할하여 다수의 프로세서에 의해 단편적으로 해결되도록 하는 것을 목적으로 합니다.오늘날 2개 이상의 코어를 가진 프로세서가 점점 더 보편화되고 있습니다.

언어들

어레이 프로그래밍 언어의 표준 예는 Fortran, APL J입니다.그 외, 다음과 같은 것이 있습니다.A+, Analytica, Chapel, IDL, Julia, K, Klong, Q, MATLAB, GNU 옥타브, PDL, R, S-Lang, SAC, Nial, ZPLTI-BASIC.

스칼라어족

C Pascal과 같은 스칼라 언어에서는 연산은 단일 값에만 적용되므로 a+b는 두 숫자의 덧셈을 나타냅니다.이러한 언어에서는 하나의 어레이를 다른 어레이에 추가하려면 인덱싱과 루프가 필요한데, 이를 코딩하는 것은 번거로운 일입니다.

위해서 (i = 0; i < > n; i++)     위해서 (j = 0; j < > n; j++)         a[i][j] += b[i][j]; 

예를 들어 Fortran 등의 어레이 기반 언어에서는 위의 중첩된 for-loop을 어레이 형식으로 한 줄에 쓸 수 있습니다.

a = a + b 

또는 오브젝트의 배열 특성을 강조하기 위해

a(:,:) = a(:,:) + b(:,:) 

C와 같은 스칼라 언어에는 네이티브 어레이 프로그래밍 요소가 포함되어 있지 않지만, 이러한 언어로 작성된 프로그램은 벡터화의 기본 기술을 이용하지 않습니다(즉, 벡터 기반 명령이 있는 경우 또는 여러 CPU 코어를 사용하는 경우).일부 최적화 수준에서 GCC와 같은 일부 C 컴파일러는 휴리스틱에 의해 유리하다고 판단되는 코드의 섹션을 검출하여 벡터화합니다. 다른 접근법은 OpenMP API를 통해 제공되며, 이를 통해 여러 CPU 코어를 활용하여 해당 코드 섹션을 병렬화할 수 있습니다.

배열 언어

어레이 언어에서는 스칼라와 어레이 모두에 적용되도록 조작이 일반화되어 있습니다.따라서 a와 b가 스칼라일 경우 a+b는 2개의 스칼라 합계를 나타내고 어레이일 경우 2개의 어레이 합계를 나타냅니다.

배열 언어는 프로그래밍을 단순화하지만 추상화 [3][4][5]패널티로 알려진 비용이 들 수 있습니다.추가는 코딩의 나머지 부분과 분리되어 수행되기 때문에 최적의 효율적인 코드를 생성하지 못할 수 있습니다(예를 들어, 같은 배열의 다른 요소 추가가 나중에 같은 실행 중에 발생하여 불필요한 반복 조회가 발생할 수 있습니다).아무리 정교한 최적화 컴파일러라도 서로 다른 프로그램 섹션이나 서브루틴에 나타나는 두 개 이상의 이질적인 함수를 결합하는 것은 매우 어렵습니다. 프로그래머가 이를 쉽게 할 수 있더라도 오버헤드를 최소화하기 위해 어레이를 통해 동일한 패스로 합계를 취합하는 것은 매우 어렵습니다.

아다

이전 C 코드는 어레이 프로그래밍 구문을 지원하는 Ada [6]언어로 다음과 같습니다.

A := A + B; 

APL

APL은 구문설탕이 없는 단일 문자 유니코드 기호를 사용합니다.

A  A + B 

이 작업은 모든 등급의 어레이(랭크 0 포함) 및 스칼라 및 어레이에서 작동합니다.Dyalog APL은 할당을 늘려서 원래 언어를 확장합니다.

A + B 

Analytica

Analytica는 Ada와 같은 표현 경제를 제공합니다.

A : = A + B;

기본의

Dartmouth BASIC은 제3판(1966년)에서 매트릭스 및 어레이 조작에 관한 MAT 문장이 있었습니다.

DIM A(4),B(4),C(4) 매트. A = 1 매트. B = 2 * A 매트. C = A + B 매트. 인쇄하다 A,B,C 

마타

Stata의 매트릭스 프로그래밍 언어 Mata는 배열 프로그래밍을 지원합니다.아래에서는 덧셈, 곱셈, 행렬과 스칼라, 요소별 곱셈, 첨자화 및 마타의 많은 역행렬 함수 중 하나를 설명한다.

. mata : : A = ( 1, 2, 3) \ ( 4, 5, 6 ) : A 1 2 3 + ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------3) : B 1 2 3 +-----------------+ 1 2 3 4 2 1 2 3 +-----+ : C = J ( 3, 2, 1) // A 3 x 2 매트릭스: C 1 +-----+ 1 2 1 1 1 +---+ 1 : D = A + 1 : 11 2 3 +-----------------+ 1 2 6 12 2 4 10 18 +---------+ : G = E :+ 3 : G 1 2 +-------------+ : H = F [ ( 2 \ 1 , ( 1 , 2 ) ] // 행렬 A의 서브스크립트화: // 대칭적 양의 반소행렬에랄화 역(F*F^(-1)F=F) : I [setric]1 2 3 +----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

매트랩

MATLAB에서 구현하면 Fortran 언어를 사용하여 동일한 경제성을 실현할 수 있습니다.

A = A + B; 

MATLAB 언어의 변형은 GNU 옥타브 언어로, 원래의 언어를 확장하여 할당을 늘립니다.

A += B; 

MATLAB와 GNU 옥타브 둘 다 기본적으로 행렬 곱셈, 행렬 반전, 선형 방정식 시스템의 수치 해법과 같은 선형 대수 연산을 지원합니다. 심지어 무어-펜로즈 의사 [7][8]역학을 사용하기도 합니다.

두 배열의 내부 곱의 Nial 예는 네이티브 행렬 곱셈 연산자를 사용하여 구현할 수 있습니다.한다면a크기가 [1n]인 행 벡터입니다.b는 크기 [n 1]의 대응하는 열 벡터입니다.

a * b;

요소 수가 동일한 두 행렬 사이의 내부 곱은 보조 연산자와 함께 구현될 수 있습니다.(:)이것은 주어진 행렬을 열 벡터로 재구성하고 전치 연산자를 만듭니다.':

A(:)" * B(:);

rasql

rasdaman 쿼리 언어는 데이터베이스 지향 배열 프로그래밍 언어입니다.예를 들어 다음 쿼리를 사용하여 두 개의 어레이를 추가할 수 있습니다.

선택한다. A + B 부터   A, B 

R

R 언어는 기본적으로 어레이 패러다임을 지원합니다.다음 예시는 2개의 행렬을 곱한 후 스칼라(실제로 단일 요소 벡터)와 벡터를 추가하는 과정을 보여 줍니다.

> A <-> 매트릭스(1:6, nrow의=2)                             # ! ! 이것은 nrow=2 ...이고 A에는 2개의 행이 있습니다. > A      [,1] [,2] [,3] [1,]    1    3    5 [2,]    2    4    6 > B <-> t( 매트릭스(6:1, nrow의=2) )  # t()는 전치 연산자 !!이것은 nrow=2 ...이고 B에는 3개의 행이 있습니다.이것은 A의 정의에 대한 명백한 모순입니다. > B      [,1] [,2] [1,]    6    5 [2,]    4    3 [3,]    2    1 > C <-> A %*% B > C      [,1] [,2] [1,]   28   19 [2,]   40   28 > D <-> C + 1 > D      [,1] [,2] [1,]   29   20 [2,]   41   29 > D + c(1, 1)  # c()는 벡터를 만듭니다.      [,1] [,2] [1,]   30   21 [2,]   42   30 

수학적 추론 및 언어 표기법

행렬 좌분할 연산자는 행렬의 의미 특성을 간결하게 표현합니다.스칼라 당량에서와 같이 (의 결정인자) 계수(행렬)가Anull이 아닌 경우 (차분) 방정식을 풀 수 있습니다.A * x = b양쪽을 역방향으로 좌회전시킴으로써A:A−1(MATLAB 언어 및 GNU 옥타브 언어:A^-1다음 수학 문장은 다음과 같은 경우에 사용됩니다.A 는 풀 랭크 스쿼어 매트릭스입니다.

A^-1 *(A * x)==A^-1 * (b)
(A^-1 * A)* x ==A^-1 * b (표준 곱셈 관련성)
x = A^-1 * b

어디에==는 등가 관계 연산자입니다.앞의 문장은 세 번째 문장이 다른 문장에 비해 먼저 실행되는 경우에도 유효한 MATLAB 식입니다(반올림 오류로 인해 수치 비교가 거짓일 수 있습니다).

시스템이 과도하게 결정되어 있는 경우 –A열보다 많은 행이 있습니다(의사 역).A+(MATLAB 및 GNU 옥타브 언어:pinv(A))는 역치환 가능A−1다음과 같습니다.

pinv(A) *(A * x)==pinv(A) * (b)
(pinv(A) * A)* x ==pinv(A) * b(표준 곱셈 관련성)
x = pinv(A) * b

그러나 이러한 솔루션은 가장 간결한 솔루션(예: 여전히 지나치게 결정된 시스템을 인지적으로 차별화할 필요성)도, 가장 계산적으로 효율적인 솔루션도 아니다.후자의 점은 스칼라 등가를 다시 고려할 때 이해하기 쉽다.a * x = b, 솔루션에서는,x = a^-1 * b보다 효율적인 작업이 아닌 두 가지 작업이 필요합니다.x = b / a문제는 일반적으로 행렬의 곱셈은 행렬의 경우 스칼라 솔루션의 확장이 다음과 같이 요구되기 때문에 가환적이지 않다는 것입니다.

(a * x)/ a ==b / a
(x * a)/ a ==b / a(행렬에는 정류성이 유지되지 않습니다!)
x * (a / a)==b / a(매트릭스에 대해서도 연관성이 유지됨)
x = b / a

MATLAB 언어는 좌측 분할 연산자를 도입합니다.\스칼라 케이스와 유추의 본질적인 부분을 유지하여 수학적 추론을 단순화하고 간결성을 유지한다.

A \ (A * x)==A \ b
(A \ A)* x ==A \ b(어소시에이티브는 매트릭스에 대해서도 유지되며, 교환성은 더 이상 필요하지 않습니다.)
x = A \ b

이것은 부호화 관점에서의 간결한 배열 프로그래밍의 예일 뿐만 아니라 계산 효율의 관점에서도 볼 수 있습니다.는 ATLAS나 [9]LAPACK과 같은 매우 효율적인 선형 대수 라이브러리에서 여러 배열 프로그래밍 언어를 활용할 수 있습니다.

Iverson의 이전 인용문으로 돌아가면, 이제 그 배경에 있는 논거가 명확해질 것입니다.

표기법의 기술 및 학습의 어려움과 그 의미를 이해하는 것의 어려움을 구별하는 것은 중요하다.예를 들어 행렬 곱을 계산하는 규칙을 배우는 것은 쉽지만, 그 의미(연관성, 덧셈에 대한 분포, 선형함수와 기하학적 연산을 나타내는 능력 등)에 대한 숙달은 훨씬 더 어렵고 다른 문제이다.실제로, 표기의 매우 암시적인 것은 그것이 탐구를 위해 제안하는 많은 특성 때문에 배우는 것을 어렵게 할 수 있다.

서드파티 라이브러리

보다 간결한 추상화를 제공하기 위해 전문적이고 효율적인 라이브러리를 사용하는 것은 다른 프로그래밍 언어에서도 일반적입니다.C++에서 몇몇 선형 대수 라이브러리는 연산자를 과부하시키는 언어의 능력을 이용한다.Python, Armadillo 및 Blitz++ 라이브러리로의 NumPy 확장 라이브러리와 같이 [10][11]이러한 언어의 매우 간결한 추상화는 어레이 프로그래밍 패러다임의 영향을 받습니다.

「 」를 참조해 주세요.

레퍼런스

  1. ^ Stéfan van der Walt; S. Chris Colbert & Gaël Varoquaux (2011). "The NumPy array: a structure for efficient numerical computation". Computing in Science and Engineering. IEEE. 13 (2): 22–30. arXiv:1102.1523. Bibcode:2011CSE....13b..22V. doi:10.1109/mcse.2011.37. S2CID 16907816.
  2. ^ Iverson, K. E. (1980). "Notations as a Tool of Thought". Communications of the ACM. 23 (8): 444–465. doi:10.1145/358896.358899.
  3. ^ Surana P (2006). Meta-Compilation of Language Abstractions (Thesis).
  4. ^ Kuketayev. "The Data Abstraction Penalty (DAP) Benchmark for Small Objects in Java". Archived from the original on 2009-01-11. Retrieved 2008-03-17.
  5. ^ Chatzigeorgiou; Stephanides (2002). "Evaluating Performance and Power Of Object-Oriented Vs. Procedural Programming Languages". In Blieberger; Strohmeier (eds.). Proceedings - 7th International Conference on Reliable Software Technologies - Ada-Europe'2002. Springer. p. 367. ISBN 978-3-540-43784-0.
  6. ^ Ada 레퍼런스 매뉴얼: G.3.1 실제 벡터와 매트릭스
  7. ^ "GNU Octave Manual. Arithmetic Operators". Retrieved 2011-03-19.
  8. ^ "MATLAB documentation. Arithmetic Operators". Retrieved 2011-03-19.
  9. ^ "GNU Octave Manual. Appendix G Installing Octave". Retrieved 2011-03-19.
  10. ^ "Reference for Armadillo 1.1.8. Examples of Matlab/Octave syntax and conceptually corresponding Armadillo syntax". Retrieved 2011-03-19.
  11. ^ "Blitz++ User's Guide. 3. Array Expressions". Archived from the original on 2011-03-23. Retrieved 2011-03-19.

외부 링크