아이콘(프로그래밍 언어)

Icon (programming language)
아이콘
Icon logo.png
패러다임멀티플렉스: 구조화, 텍스트 지향
설계자랄프 그리즈월드
처음 등장한1977년; 45년 전 (연방)
안정된 릴리스
9.5.20 / 2020년 8월 13일, 23개월 전(2020-08-13)[1]
타이핑 분야역학
웹 사이트www.cs.arizona.edu/icon
주요 구현
아이콘, Jcon
사투리
유니콘
영향을 받다
SNOBOL, SL5, ALGOL
영향받은
Unicon, Python, Galdi

Icon은 "목표 지향 실행" 개념에 기초한 매우 높은 수준의 프로그래밍 언어입니다. 여기서 코드는 유효한 값 또는 "실패"와 함께 "성공"을 반환하며 반환할 유효한 데이터가 없음을 나타냅니다.주어진 코드 블록의 성공과 실패는 추가 처리를 지시하는 데 사용되는 반면, 기존 언어는 일반적으로 프로그래머가 동일한 목적을 달성하기 위해 작성한 부울 논리를 사용합니다.기본 제어 구조의 논리는 아이콘에 암묵적으로 포함되어 있는 경우가 많기 때문에 일반적인 작업은 덜 명시적인 코드로 완료할 수 있습니다.

Icon은 랄프 그리즈월드가 SNOBOL 언어에 기여한 Bell Labs를 떠난디자인되었습니다.SNOBOL은 1970년대 초반의 표준으로 볼 때 오래된 구문을 가진 문자열 처리 언어였다.애리조나 대학으로 옮긴 후, 그는 SL5에서 더 기초가 되는 SNOBOL 개념을 개발했지만, 결과는 실패라고 생각했다.이것은 SNOBOL과 같은 언어의 짧지만 개념적으로 조밀한 코드와 C나 Pascal과 같은 ALGOL에서 영감을 받은 언어의 보다 친숙한 구문을 혼합한 상당히 업데이트된 아이콘으로 이어졌다.

영감을 준 언어와 마찬가지로 Icon의 주요 사용 분야는 문자열과 텍스트 패턴을 관리하는 것입니다.예를 들어 "world"에서 "the"를 찾을 때 문자열 작업이 실패하는 경우가 많습니다.대부분의 언어에서는 유효하지 않은 결과를 사용하지 않기 위해 테스트와 분기가 필요합니다.아이콘에서 이러한 종류의 테스트는 대부분 필요하지 않으므로 프로그래머가 작성하는 코드 양이 줄어듭니다.복잡한 패턴 처리는 Perl과 같은 전용 언어와 비슷하지만 다른 ALGOL과 유사한 언어의 사용자에게 익숙한 기능 지향 구문을 유지하는 몇 줄의 간결한 코드로 이루어질 수 있습니다.

Icon은 객체 지향적인 것이 아니라, 1996년에 객체 지향적인 확장 Idol이 개발되었고, 결국 Unicon이 되었다.또한 다른 언어에도 영감을 주었으며, 특히 심플한 생성기가 영향을 미쳤습니다. Icon의 생성기는 Python 프로그래밍 [2]언어에 큰 영감을 주었습니다.

역사

스누볼

SNOBOL1로 소급하여 알려진 최초의 SNOBOL 노력은 1962년 가을 Bell Labs Programming Research [3]Department에서 시작되었습니다.그 노력은 다항식 조작, 기호 통합 및 마르코프 연쇄 연구를 위해 SCL 언어를 사용하려다 좌절된 것에 대한 반응이었다.SCL은 Chester Lee 부장에 의해 작성되었으며 속도가 느리고 구문이 낮아서 간단한 프로젝트에서도 대량의 코드가 생성되었습니다.COMIT 언어를 잠시 생각한 후, 6명의 부서 멤버인 Ivan Polonsky, Ralph Griswold, 그리고 David Farber는 이 [4]문제들을 해결하기 위해 그들만의 언어를 쓰기로 결정했다.

최초의 버전은 1963년 에 IBM 7090에서 실행되었으며, 여름 무렵에는 Bell에서 구축되어 사용되고 있었습니다.이것은 거의 즉시 SNOBOL2로 이어졌고, 이것은 많은 내장 함수와 외부 어셈블리 언어 코드에 링크하는 기능을 추가했다.1964년 4월에 출시되어 주로 Bell 내에서 사용되었지만 Project MAC에서도 일부 사용되었습니다.시스템 기능의 도입은 주로 [5]1964년 7월에 출시된 SNOBOL3의 주요 특징이었던 사용자 기능의 필요성을 나타내기 위한 것이었다.

SNOBOL3의 도입은 벨 랩 컴퓨팅 부서 내의 주요 변화와 일치하며, 여기에는 SNOBOL의 개서를 필요로 하는 새로운 GE 645 메인프레임의 추가가 포함됩니다.대신, 팀은 SNOBOL Intermediate Language용 SIL이라는 가상 머신에서 실행되는 새로운 버전을 작성하여 충분히 강력한 플랫폼으로 쉽게 이식할 수 있도록 할 것을 제안했습니다.이 제안은 1965년 9월에 SNOBOL4로 받아들여졌다.이 무렵,[6] 1966년 8월에 상당히 개선된 버전의 언어에 대한 계획이 나타났다.언어에 대한 추가 작업은 1960년대 내내 계속되었으며, 특히 이후 버전에서 연관 배열 유형을 추가했는데, 이들은 이를 표라고 불렀습니다.

SL5는 아이콘으로 이어집니다.

그리즈월드는 1971년 [7]8월 벨 연구소를 떠나 애리조나 대학의 교수가 되었다.그는 당시 [8]연구 도구로 SNOBOL4를 도입했다.

원래 1960년대 초에 개발된 언어로서, SNOBOL의 구문은 FORTRAN과 COBOL같은 다른 초기 프로그래밍 언어의 특징을 가지고 있다.특히 이러한 언어 중 많은 수가 컬럼 레이아웃이 자연스러운 펀치 카드에 입력되었기 때문에 언어는 컬럼에 의존합니다.또한 제어 구조는 ALGOL 60의 도입 이후 필수 기능이 되어가고 있는 블록의 사용보다는 거의 전적으로 코드 주변의 분기에 기반을 두고 있었습니다.그가 애리조나로 이사했을 때 SNOBOL4의 구문은 절망적으로 [9]구식이었다.

Griswold는 if/then과 같은 전통적인 흐름 제어 구조를 사용하여 SNOBOL의 근본적인 성공/실패 개념을 구현하기 위한 노력을 시작했습니다.이것은 "SNOBOL Language 5"의 줄임말인 SL5가 되었지만,[9] 결과는 만족스럽지 못했다.1977년, 그는 새로운 버전을 고려하기 위해 그 언어로 돌아왔다.그는 SL5에서 도입된 매우 강력한 기능 시스템을 단순한 일시정지/재개 개념으로 포기하고 다음과 같은 [9]원리로 SNOBOL4의 자연스러운 후계자를 위한 새로운 개념을 개발했습니다.

  • SNOBOL4의 철학적, 반론적 기반
  • SL5 구문 기반
  • SL5 기능(일반화된 절차 메커니즘 제외)

이 새로운 언어는 처음에는 SNOBOL5로 알려졌지만, 기본 개념을 제외한 모든 면에서 SNOBOL과 상당히 달랐기 때문에 결국 새로운 이름이 필요했습니다."s"를 "C"에 대한 일종의 오마주라고 생각한 후, 그 이름을 사용한 문서의 조판 문제로 인해 결국 포기되었다.어빙, 바드, 그리고 "언어"의 "TL"이라는 새로운 이름들이 제안되고 버려졌다.시기에 Xerox PARC는 그래픽 사용자 인터페이스에 대한 그들의 작업에 대해 출판하기 시작했고 "아이콘"이라는 용어가 컴퓨터 어휘에 포함되기 시작했다.처음에 이름을 "아이콘"으로 변경한 후 "아이콘"[9]을 선택하기로 결정했습니다.

언어

기본 구문

Icon 언어는 구조화된 프로그래밍 언어의 ALGOL 클래스에서 파생되었기 때문에 C 또는 Pascal과 유사한 구문을 가지고 있습니다.아이콘은 Pascal과 가장 유사하며,:=할당 구문,procedure키워드 및 유사한 구문입니다.한편 Icon은 실행 그룹을 구성하기 위해 C-스타일 중괄호를 사용하며 프로그램은 다음과 같은 절차를 실행함으로써 시작됩니다.main를 클릭합니다.[10]

또한 Icon은 대부분의 스크립트 언어(SNOBOL 및 SL5)와 기능을 공유합니다. 변수는 선언할 필요가 없으며, 유형은 자동으로 캐스팅되며, 숫자는 자동으로 [11]문자열로 변환되고 다시 돌아올 수 있습니다.모든 스크립트 언어에서 공통되는 또 다른 기능은 줄 바꿈 문자가 없다는 것입니다.아이콘에서 세미콜론으로 끝나지 않는 행은 [12]의미가 있는 경우 암묵적인 세미콜론으로 끝납니다.

절차는 아이콘 프로그램의 기본 구성 요소입니다.비록 그들은 파스칼 이름을 사용하지만, 그들은 C 함수와 더 비슷하게 작동하고 값을 반환할 수 있습니다; 없습니다.function키워드를 지정합니다.[13]

 절차. 어떻게 좀 해봐.(a스트링)    쓰다(a스트링)  끝. 

목표 지향 실행

SNOBOL의 주요 개념 중 하나는 함수가 매직 넘버나 다른 [14][15]기술을 사용하는 대신 언어의 원점으로 "성공" 또는 "실패"를 반환한다는 것이었다.예를 들어, 다른 문자열 내의 하위 문자열의 위치를 반환하는 함수는 대부분의 언어 런타임 시스템에서 볼 수 있는 일반적인 루틴입니다; 자바스크립트에서는 "Hello, World!" 내에서 "World"라는 단어의 위치를 찾기를 원할 수 있습니다.position = "Hello, World".indexOf("World")7이 반환됩니다.대신 어떤 사람이 요구하면position = "Hello, World".indexOf("Goodbye")검색어가 문자열에 표시되지 않기 때문에 코드가 "실패"합니다.자바스크립트에서는 대부분의 언어와 마찬가지로 매직넘버(이 경우 -1)[16]를 반환함으로써 표시됩니다.

SNOBOL에서는 이런 종류의 장애가 발생하면 특별한 값이 반환됩니다.failSNOBOL의 구문은 동작의 성공 또는 실패에 따라 직접 동작하며 별도의 테스트를 작성할 필요 없이 코드의 라벨이 붙은 섹션으로 이동합니다.예를 들어, 다음 코드는 "Hello, world!"를 5회 [17]인쇄합니다.

* Hello World를 인쇄하는 SNOBOL 프로그램       I = 1 고리  산출량 = "안녕, 세상아!"       I = I + 1       LE(I, 5) : S(고리) 끝. 

루프를 실행하려면 , less-an-equal 연산자,LE는 인덱스 변수 I에서 호출됩니다.Succeeds, 즉 내가 5살 미만임을 의미하며 이름 있는 라벨에 분기합니다.LOOP계속합니다.[17]

Icon은 성공 또는 실패에 따른 흐름 제어 개념을 유지하면서도 언어를 더욱 발전시켰습니다.한 가지 변경은 라벨이 부착된 제품을 교체한 것입니다.GOTO1960년대 [9]후반 컴퓨터 업계를 휩쓸었던 구조화된 프로그래밍 스타일에 맞춰 블록 지향 구조를 가진 분기처럼.두 번째는 전체 블록이 성공 또는 실패하도록 콜 체인을 따라 "실패"를 전달할 수 있도록 하는 것이었습니다.이것은 아이콘 언어의 주요 개념입니다.기존 언어에서는 부울 논리에 따라 성공 또는 실패를 테스트하고 그 결과에 따라 분기하는 코드를 포함해야 하는 반면, 이러한 테스트와 브랜치는 아이콘 코드에 고유하며 명시적으로 [18]기술할 필요가 없습니다.

예를 들어 Java 프로그래밍 언어로 작성된 이 코드 비트를 생각해 보십시오.함수를 호출합니다.read()(이전 열린) 파일에서 문자를 읽으려면 결과를 변수에 할당합니다.a,그리고 나서.write의 가치a다른 파일로 이동합니다.그 결과, 1개의 파일이 다른 파일에 카피됩니다. read파일로부터 읽어낼 문자가 없어지는 것은, 최초의 콜에 대해서가 될 가능성이 있기 때문에, 이 경우,a미정의 상태로 잠재적으로 원인이 되는writeNull 포인터 예외를 발생시킵니다.이걸 피하기 위해서read특수값을 반환합니다.EOF이 상황에서는 (파일 끝)을 사용하지 않으려면 명시적 테스트가 필요합니다.write입력:

 하는 동안에 ((a = 읽어주세요()) != EOF) {    쓰다(a);  } 

대조적으로 아이콘에서는read()함수는 텍스트 행을 반환합니다.&fail.&fail단순한 유사점이 아니다EOF이는 문맥에 따라 "처리 중지" 또는 "실패 사례 수행"을 의미하는 것으로 언어에서 명확하게 이해되기 때문입니다.아이콘의 동등한 코드는 다음과 같습니다.[15]

 하는 동안에 a := 읽어주세요() 그리고나서 쓰다(a) 

즉, "읽기에 실패하지 않는 한, 쓰기를 호출하고, 그렇지 않으면 중지합니다."[15]Java 예시와 같이 매직 넘버에 대한 테스트를 지정할 필요가 없습니다.이것은 암묵적인 것으로, 결과 코드는 심플화됩니다.성공과 실패는 콜체인을 통해 전달되므로 다른 함수에 함수를 삽입할 수 있으며 중첩된 함수가 실패하면 기능이 정지됩니다.예를 들어, 위의 코드를 다음과 같이 [19]줄일 수 있습니다.

 하는 동안에 쓰다(읽어주세요()) 

이 버전에서는read실패,write에러가 발생하며,while중지.[19] 아이콘의 분기 및 루프 구조는 모두 프로그래머가 제공하는 임의의 부울 테스트가 아닌 내부 코드의 성공 또는 실패를 기반으로 합니다. if를 실행합니다.then블록의 "test"가 값을 반환하는 경우,else반환되는 경우 차단하거나 다음 행으로 이동하는&fail.저도 마찬가지예요.while는 장애를 수신할 때까지 블록을 계속 호출합니다.아이콘은 이 개념을 목표 지향 [20]실행이라고 합니다.

성공과 실패의 개념을 예외의 개념과 비교하는 것이 중요합니다. 예외는 예상된 결과가 아니라 특이한 상황입니다.아이콘에서 실패는 예상된 결과입니다.파일 끝에 도달하는 것은 예상된 상황이며 예외가 아닙니다.아이콘에는 전통적인 의미의 예외 처리는 없지만 예외와 유사한 상황에서 실패가 자주 사용됩니다.예를 들어, 읽고 있는 파일이 존재하지 않는 경우,read특별한 상황이 [15]표시되지 않으면 실패합니다.전통적인 언어에서는 이러한 "기타 조건"은 자연스러운 표시 방법이 없습니다. 추가 매직 넘버를 사용할 수도 있지만, 보다 일반적으로 예외 처리를 사용하여 값을 "투척"합니다.예를 들어 Java 코드에서 누락된 파일을 처리하기 위해 다음과 같이 표시될 수 있습니다.

 해라 {    하는 동안에 ((a = 읽어주세요()) != EOF) {      쓰다(a);    }  } 또 만나 (예외. e) {    // 다른 문제가 발생했습니다. 이 캐치를 사용하여 루프를 종료합니다.  } 

이 경우 EOF용과 기타 모든 오류용 두 가지 비교가 필요합니다.Java는 Icon에서와 같이 예외를 논리 요소로 비교하는 것을 허용하지 않기 때문에 다음과 같은 장황한 명령어는try/catch대신 구문을 사용해야 합니다.Try blocks는 예외가 발생하지 않더라도 Icon이 일반적으로 회피하는 분산 비용인 성능 저하를 초래합니다.

Icon은 이와 같은 목표 지향 메커니즘을 사용하여 기존의 부울 테스트를 수행합니다.단, 미묘한 차이는 있습니다.다음과 같은 간단한 비교if a < b then write("a is smaller than b")는 대부분의 언어에서와 같이 "오른쪽 연산이 참으로 평가되는 경우"를 의미하는 것이 아니라 "오른쪽 연산이 성공하는 경우"와 같은 의미입니다.이 경우,<비교가 참일 경우 연산자가 성공합니다.if그것을 호출하다then표현에 성공했을 경우, 또는else또는 실패 시 다음 행으로 이동합니다.그 결과는 다른 언어에서 볼 수 있는 기존의 if/when과 비슷합니다.if실행하다then한다면a보다 작다b미묘한 점은 동일한 비교 표현을 어디에나 배치할 수 있다는 것입니다. 예를 들어 다음과 같습니다.

 쓰다(a < > b) 

또 다른 차이점은 다음과 같습니다.<operator가 성공하면 두 번째 인수를 반환합니다.이 예에서는 값이 다음과 같습니다.b만약 그것이 더 크다면 쓰여질 것이다a그렇지 않으면 아무것도 기록되지 않습니다.이것은 테스트 그 자체가 아니라 값을 반환하는 연산자이기 때문에, 다음과 같은 것들을 가능하게 할 수 있습니다.if a < b < c대부분의 언어에서 다음과 같은 두 부등식의 결합으로 쓰여져야 하는 공통적인 비교 유형입니다.[19]if (a < b) && (b < c).

목표 지향 실행의 중요한 측면은 프로시저가 실패하면 프로그램이 이전 상태로 되감아야 한다는 것입니다. 이 작업은 역추적이라고 알려져 있습니다.예를 들어 변수를 시작 위치로 설정한 다음 값을 변경할 수 있는 작업을 수행하는 코드를 고려하십시오. 예를 들어 문자열 검색 작업에서는 검색 시 커서를 문자열에서 이동시키는 것이 일반적입니다.이 절차가 실패했을 경우, 그 변수의 후속 읽기는 내부에서 조작되고 있던 상태가 아니라 원래 상태를 반환하는 것이 중요합니다.이 태스크의 경우 Icon에는 되돌릴 수 있는 할당 연산자가 있습니다.<-, 및 역방향 교환,<->예를 들어, 큰 문자열 내에서 패턴 문자열을 찾으려는 코드를 생각해 보겠습니다.

 {    (i := 10) &    (j := (i < > 발견하다(양식, 입력 문자열)))  } 

이 코드는 이동부터 시작합니다.i검색 시작 위치인 10까지를 선택합니다.다만,find블록 전체가 실패하기 때문에 그 결과,i바람직하지 않은 부작용으로 10시에 남겨지는 것.교환i := 10와 함께i <- 10를 나타냅니다.i블록이 실패하면 이전 값으로 재설정해야 합니다.이는 실행 시 원자성의 유사성을 제공합니다.

제너레이터

예를 들어 아이콘의 식은 단일 값을 반환할 수 있습니다.5 > x는 x 값이 5보다 작을 경우 x를 평가하여 반환합니다.그렇지 않을 경우 실패합니다.그러나 Icon에는 성공 또는 실패를 즉시 반환하지 않고 호출될 때마다 새 값을 반환하는 프로시저 개념도 포함되어 있습니다.이들은 생성기로 알려져 있으며 아이콘 언어의 중요한 부분입니다.Icon의 용어로 표현식 또는 함수를 평가하면 결과 시퀀스가 생성됩니다.결과 시퀀스에는 식 또는 함수에 의해 생성될 수 있는 모든 가능한 값이 포함됩니다.결과 시퀀스가 모두 사용되면 식 또는 함수가 실패합니다.

아이콘을 사용하면 프로시저가 1개의 값 또는 여러 개의 값을 반환할 수 있습니다.fail,return그리고.suspend키워드를 지정합니다.다음 키워드 중 하나가 없는 프로시저는&fail에 대한 실행이 실행될 때마다 발생합니다.end의 절차입니다.예:

 절차. f(x)    한다면 x > 0 그리고나서 {      돌아가다 1    }  끝. 

부르기f(5)1은 반환되지만,f(-1)돌아온다&fail이 경우, 예를 들어 불분명한 동작이 발생할 수 있습니다.write(f(-1))아무것도 출력되지 않습니다.f장애가 발생하여 동작을 정지합니다.write를 클릭합니다.[21]

프로시저를 제너레이터로 변환하려면suspend키워드: "이 값을 반환하고 다시 호출하면 이 시점에서 실행을 시작합니다"를 의미합니다.이 점에 있어서 그것은 일종의 조합과 같다.staticC의 개념과return. 예:[15]

 절차. 이토J(i, j)    하는 동안에 i <=> j 하다 {      일시 정지하다 i      i +:= 1    }    실패하다  끝. 

에서 시작하는 일련의 숫자를 반환하는 생성기를 만듭니다.i그리고 끝은j를 반환한다.&fail[a]후에.suspend i실행을 중지하고 값을 반환합니다.i상태를 리셋하지 않고 말이죠.같은 함수에 다른 콜이 발신되었을 경우, 그 시점에서 이전 값을 사용하여 실행이 픽업됩니다.이 경우, 이 경우, 이 동작으로 인해i +:= 1while 블록의 선두로 루프백한 후 다음 값을 반환하고 다시 일시정지합니다.이것은 다음까지 계속됩니다.i <= j에러가 발생하고, 그 시점에서 블록에서 나와 콜을 호출합니다.fail이를 통해 반복기[15]쉽게 구성할 수 있습니다.

발전기-빌더의 또 다른 유형은 교류발전기로, 부울처럼 보이고 작동합니다.or교환입니다.예:

 한다면 y < > (x   5) 그리고나서 쓰다("y=", y) 

이는 "y가 x 또는 5보다 작으면..."이라고 말하는 것처럼 보이지만 실제로는 목록의 끝에서 떨어질 때까지 값을 반환하는 제너레이터의 단축형입니다.이 경우 목록의 값은 작업에 "주입"됩니다.<이 예에서는 시스템이 먼저 y < x 를 테스트합니다.x 가 실제로 y 보다 클 경우 x 의 값이 반환되고, 테스트에 합격하여 y 의 값이 에 써집니다.then절을 클릭합니다.단, x가 y보다 크지 않으면 장애가 발생하며 교류발전기는 y < 5를 계속 실행합니다.그 테스트에 합격하면 y가 기입됩니다.y가 x 또는 5보다 작을 경우 교류발전기는 테스트가 부족하여 실패합니다.if에러가 발생하며,write는 실행되지 않습니다.따라서 x 또는 5보다 작을 경우 y 값이 콘솔에 표시되므로 부울의 목적을 충족합니다.or파라미터의 평가가 성공하지 않는 한 함수는 호출되지 않으므로 이 예는 다음과 같이 단축할 수 있습니다.

 쓰다("y=", (x   5) > y) 

내부적으로는 교류 발전기가 단순하게or또, 임의의 값 리스트를 작성하기 위해서도 사용할 수 있습니다.이것은 다음과 같은 임의의 값에 대해 반복할 때 사용할 수 있습니다.

 모든 i := (1 3 4 5 10 11 23) 하다 쓰다(i) 

정수 리스트는 많은 프로그래밍 컨텍스트에서 흔히 볼 수 있기 때문에 Icon은 또한 다음을 포함합니다.to키워드를 지정하여 애드혹 정수 생성기를 만듭니다.

 모든 k := i 로. j 하다 쓰다(k) 

단축할 수 있습니다.

 모든 쓰다(1 로. 10) 

아이콘은 강하게 입력되지 않으므로 교류발전기 목록에 다른 유형의 항목이 포함될 수 있습니다.

 모든 i := (1   "안녕하세요"   x < > 5)  하다 쓰다(i) 

x의 값에 따라 1, "hello" 및 5로 표시됩니다.

마찬가지로 접속 연산자도&는 부울과 같은 방법으로 사용됩니다.and연산자:[22]

 모든 x := 이토J(0,10) & x % 2 == 0 하다 쓰다(x) 

이 코드는ItoJx에 할당된 초기값 0을 반환합니다.그런 다음 연결의 오른쪽을 수행합니다.x % 20 이 되어, 값이 써집니다.그런 다음 콜을 합니다.ItoJ1에서 x를 할당하는 제너레이터가 다시 생성되어 우측에 실패하고 아무것도 인쇄되지 않습니다.결과는 0 ~ [22]10의 모든 짝수 정수 목록입니다.

생성기 개념은 문자열 연산에 사용할 때 특히 유용하고 강력하며 Icon 전체 설계의 기본 기반이 됩니다.고려 사항:indexOf여러 언어로 검색된 작업. 이 함수는 다른 문자열 내에서 한 문자열을 검색하여 해당 위치의 인덱스를 반환하거나 찾을 수 없는 경우 매직 번호를 반환합니다.예:

 s = "세상은 모두 무대다.그리고 남녀 모두 선수일 뿐이다.;  i = 색인("the" (the), s);  쓰다(i); 

그러면 문자열이 검색됩니다.s"the"의 첫 번째 항목을 찾아 인덱스를 반환합니다(이 경우 4).그러나 이 문자열에는 문자열 "the"의 인스턴스가 2개 포함되어 있기 때문에 두 번째 예를 반환하려면 대체 구문을 사용합니다.

 j = 색인("the" (the), s, i+1);  쓰다(j); 

위치 5부터 검색하도록 지시하므로 이전에 찾은 첫 번째 인스턴스와 일치하지 않습니다.단, "the"의 두 번째 인스턴스가 없을 수 있습니다.첫 번째 인스턴스가 없을 수도 있습니다.따라서 다음 값에서 반환되는 값은indexOf매직 넘버 -1과 대조해야 합니다. 매직 넘버 -1은 일치하지 않음을 나타냅니다.모든 인스턴스의 위치를 출력하는 완전한 루틴은 다음과 같습니다.

 s = "세상은 모두 무대다.그리고 남녀 모두 선수일 뿐이다.;  i = 색인("the" (the), s);  하는 동안에 i != -1 {    쓰다(i);    i =  색인("the" (the), s, i+1);  } 

아이콘에서 동등한 값find는 제너레이터이므로 동일한 결과를 한 줄로 작성할 수 있습니다.

 s := "세상은 모두 무대다.그리고 남녀 모두 선수일 뿐이다.  모든 쓰다(발견하다("the" (the), s)) 

물론 입력 후 문자열을 찾고 싶은 경우가 있습니다. 예를 들어 처음 4개의 열에 행 번호가 포함된 텍스트 파일을 스캔하고 공백이 있는 경우, 그 다음 텍스트 행을 스캔하는 경우입니다.목표 지향 실행을 사용하여 회선 번호를 건너뛸 수 있습니다.

 모든 쓰다(5 < > 발견하다("the" (the), s)) 

이 위치는 위치 5 뒤에 "the"가 표시될 경우에만 반환됩니다.그렇지 않을 경우 비교는 실패하고 기입에 실패하며 쓰기는 실행되지 않습니다.

every연산자는 와 유사합니다.while제너레이터에 의해 반환된 모든 항목을 루프하고 [21]장애 발생 시 종료:

  모든 k := i 로. j 하다     쓰다(일부 기능(k)) 

사이에는 중요한 차이가 있다every그리고.while;while첫 번째 결과가 실패할 때까지 재평가합니다.every제너레이터에서 다음 값을 가져옵니다. every실제로 Smalltalk 아래의 블록과 유사한 방식으로 함수에 값을 주입합니다.예를 들어, 위의 루프는 다음과 [21]같이 고쳐 쓸 수 있습니다.

 모든 쓰다(일부 기능(i 로. j)) 

이 경우 i에서 j까지의 값이 다음 중 하나에 주입됩니다.someFunction출력의 [21]여러 행을 기입합니다.

컬렉션

아이콘에는 스택 및 , 테이블(다른 언어에서는 지도 또는 사전이라고도 함), 세트 등으로 사용할 수 있는 목록 등 여러 가지 컬렉션 유형이 있습니다.아이콘은 이들을 구조물이라고 합니다.컬렉션은 고유한 생성기로 bang 구문을 사용하여 쉽게 호출할 수 있습니다.예:

 줄들 := []                    # 빈 목록을 만듭니다.  하는 동안에  := 읽어주세요() 하다 {      # 표준 입력에서 라인을 읽는 루프 수    밀다(줄들, )            # stack like 구문을 사용하여 목록의 행을 푸시합니다.  }  하는 동안에  := (줄들) 하다 {  # loop (목록에서 행을 삭제할 수 있는 동안)    쓰다()                  # 행아웃  } 

위의 예에서 보듯이 장애 전파를 사용하여 테스트와 루프를 조합할 수 있습니다.

 줄들 := []                    # 빈 목록을 만듭니다.  하는 동안에 밀다(줄들, 읽어주세요())      # 비워질 때까지 누르다  하는 동안에 쓰다((줄들))        # 비워질 때까지 쓰기 

목록 수집은 생성기이므로 bang 구문을 사용하여 이를 더욱 단순화할 수 있습니다.

 줄들 := []  모든 밀다(줄들, !입력)  모든 쓰다(!줄들) 

이 경우, Bang in은write아이콘은 배열에서 텍스트 행을 하나씩 반환하고 마지막에 실패합니다. &input의 발전기 기반 아날로그입니다.read표준 입력의 을 읽을 수 있습니다.!&input는 파일이 끝날 때까지 행을 계속 읽습니다.

아이콘은 유형이 없기 때문에 목록에는 다음과 같은 다양한 유형의 값을 포함할 수 있습니다.

고양이 := ["인쇄", , 2002, 8] 

항목에는 다른 구조물이 포함될 수 있습니다.더 큰 목록을 작성하기 위해 아이콘에는list발전기i := list(10, "word")는 10개의 "word" 복사본을 포함하는 목록을 생성합니다.다른 언어의 어레이와 마찬가지로 Icon을 사용하면 다음과 같은 항목을 위치별로 검색할 수 있습니다.weight := aCat[4]어레이 슬라이싱이 포함되어 있기 때문에 예를 들어 다른 리스트의 요소에서 새로운 리스트를 작성할 수 있습니다.aCat := Cats[2:4]는 "tabby" 및 2002를 포함하는 aCat이라는 새 목록을 생성합니다.

테이블은 기본적으로 정수가 아닌 임의의 인덱스 키가 있는 목록입니다.

 기호 := 테이블(0)  기호["거기"] := 1  기호["여기"] := 2 

이 코드는 알 수 없는 키의 기본값으로 0을 사용하는 테이블을 만듭니다.그런 다음 "there" 및 "here" 키와 값 1 및 2를 사용하여 테이블에 두 항목을 추가합니다.

세트도 리스트와 비슷하지만 지정된 값의 멤버는 1개뿐입니다.아이콘에는 다음이 포함됩니다.++두 세트의 결합을 생산하기 위해**교차로, 그리고--차액아이콘에는 다양한 문자가 포함된 집합인 사전 정의된 "Cset"이 다수 포함되어 있습니다.아이콘에는 4개의 표준 Cset이 있습니다.&ucase,&lcase,&letters,그리고.&digits예를 들어 문자열을 작은 따옴표로 묶어서 새로운 Cset을 만들 수 있습니다.vowel := 'aeiou'.

줄들

아이콘에서 문자열은 문자 목록입니다.목록으로, 이들은 생성기이므로 bang 구문을 사용하여 반복할 수 있습니다.

 쓰다(!"안녕, 세상아!") 

문자열의 각 문자를 다른 행에 인쇄합니다.

괄호내의 범위 지정을 사용하고, 문자열로부터 기판을 추출할 수 있다.범위 지정은 점을 단일 문자 또는 문자열의 슬라이스로 반환할 수 있습니다.문자열은 오른쪽 또는 왼쪽에서 인덱싱할 수 있습니다.문자열 내의 위치는 문자 ABC234 사이에 정의되며 오른쪽−2−10 ABC부터 지정할 수 있습니다.

예를들면,

 "위키피디아"[1]     ==> 'W'  "위키피디아"[3]     ==> "k"  "위키피디아"[0]     ==> "a"  "위키피디아"[1:3]   ==> '위'  "위키피디아"[-2:0]  ==> "ia"  "위키피디아"[2+:3]  ==> "iki" 

마지막 예에서는 끝 위치 대신 길이를 사용하는 방법을 보여 줍니다.

첨자 규격은 식 내에서 l 으로 사용할 수 있습니다.이것은 문자열을 다른 문자열에 삽입하거나 문자열의 일부를 삭제하는 데 사용할 수 있습니다.예를 들어 다음과 같습니다.

    s := "실패"     s[2] := "123"     s 지금이다 가지다 a 가치  "a123c"     s := "defg"     s[3:5] := "ABCD     s 지금이다 가지다 a 가치  ABCDefg     s := "defg"     s[3:5] := ""     s 지금이다 가지다 a 가치  "아베그" 

문자열 스캔

스트링의 취급을 한층 더 심플하게 하는 것은, 스캔 시스템입니다.스캔 시스템은?이 명령어는 문자열의 함수를 호출합니다.

 s ? 쓰다(발견하다("the" (the))) 

아이콘은 의 왼쪽을 나타냅니다.?서브젝트로 간주하여 문자열 함수로 전달합니다.를 호출합니다.find는 파라미터 1로 검색 텍스트와 파라미터 2로 검색할 문자열의 두 가지 파라미터를 사용합니다.사용.?두 번째 파라미터는 암묵적이며 프로그래머가 지정할 필요가 없습니다.하나의 문자열로 여러 함수를 순차적으로 호출하는 일반적인 경우, 이 스타일은 결과 코드의 길이를 크게 줄이고 명확성을 향상시킬 수 있습니다.아이콘 함수 시그니처는 정의에서 서브젝트 파라미터를 식별하기 때문에 파라미터를 이 방법으로 올릴 있습니다.

?는 단순히 구문설탕의 형태가 아니라 다음 문자열 연산을 위한 "문자열 스캔 환경"을 설정합니다.이는 두 가지 내부 변수를 기반으로 합니다.&subject그리고.&pos;&subject는 원래 문자열에 대한 포인터일 뿐이지만,&pos현재 위치 또는 커서입니다.Icon의 다양한 문자열 조작 프로시저는 이 두 변수를 사용하기 때문에 프로그래머가 명시적으로 제공할 필요가 없습니다.예를 들어 다음과 같습니다.

  s := "이건 스트링이에요"   s ? 쓰다("param=[",&quot;&quot; (&quot;)," , pos = [ ",&pos,"]") 

다음과 같은 결과가 다음과 같습니다.

subject=[이것은 문자열입니다], pos=[1]

기본 제공 및 사용자 정의 함수를 사용하여 검색 중인 문자열 내에서 이동할 수 있습니다.모든 기본 제공 함수는 기본적으로 다음과 같습니다.&subject그리고.&pos검색 구문을 사용할 수 있습니다.다음 코드는 공백으로 구분된 모든 "words"를 문자열에 기록합니다.

  s := "이건 스트링이에요"   s ? {                               # 문자열 검색 환경 구축       하는 동안에 것은 아니다. 포스(0) 하다  {          # 문자열 끝 테스트           (많이(' '))              # 빈칸은 건너뛰고           단어 := (까지(' ')   0)  # 다음 단어는 다음 공백 또는 줄의 끝에 있습니다.           쓰다(단어)                 # 단어를 써라       }   } 

이 예에서는 많은 새로운 기능이 도입되어 있습니다. pos의 현재 값을 반환합니다.&pos이 기능을 필요로 하는 이유는 명확하지 않을 수 있습니다.단순히 이 기능을 사용하지 않는 이유는 명확하지 않을 수 있습니다.&pos직접; 그 이유는&pos변수이므로 값을 취할 수 없습니다.&fail이 순서는,pos할 수 있다. 따라서pos에 경량 래퍼를 제공합니다.&posIcon의 목표 지향 흐름 제어를 쉽게 사용할 수 있도록 하기 위해 손으로 쓴 부울 테스트를 제공할 필요가 없습니다.&pos이 경우 테스트는 "is &pos 제로"입니다.이는 Icon 문자열 위치의 홀수 번호로 행의 끝입니다.0이 아니면pos돌아온다&fail, 이것은, 와 함께 반전됩니다.not루프가 계속됩니다.

many현재에서 시작하는 제공된 Cset 파라미터의 예를 하나 이상 찾습니다.&pos이 경우 공백 문자를 찾고 있기 때문에 이 함수의 결과는 공백이 아닌 첫 번째 문자 위치입니다.&pos.tab움직인다&pos그 장소까지, 다시 한 번 가능성을 가지고&fail예를 들어,many줄 끝에서 떨어집니다. upto본질적으로 반대이다many; 이것은 제공된 Cset의 바로 앞에 있는 위치를 반환합니다.이 예에서는 이 Cset의 설정을 다음에 실시합니다.&pos타인과 함께tab. 교대로 행의 끝에서 정지합니다.

이 예에서는 마침표, 쉼표 및 기타 구두점뿐만 아니라 탭이나 공백이 없는 공백 문자를 포함하는 보다 적절한 "word breaking" Cset을 사용하여 보다 견고하게 만들 수 있습니다.이 Cset은 다음에서 사용할 수 있습니다.many그리고.upto.

보다 복잡한 예는 생성기와 문자열 스캔이 언어 내에 통합되어 있음을 보여줍니다.

 절차. 주된()      s := "12월 8일 월요일"      s ? 쓰다(날짜()   "유효한 날짜가 아닙니다")  끝.  # 반환되는 일치 함수를 정의합니다.  # 월의 요일과 일치하는 문자열  절차. 날짜()  # 초기값의 정의  정적인 날짜  정적인 날들  초기의 {         날들 := ['월','화',"수요일","Thr",'금요일','토','태양']         몇달. := ["Jan",'2월','마루','4월','5월','준',                   '줄','8월',,'10월','11월','12월']  }  모든 일시 정지하다   (회수하다 <->  (경기(!날들))        # 하루 일치                              =" "                     # 뒤에 공백이 있다                              (경기(!몇달.))      # 다음 달                              =" "                     # 뒤에 공백이 있다                              매치 디짓(2)           # 뒤에 2자리 이상 붙습니다.                  ) &                  (=" "   포스(0) ) &                   # 공백 또는 문자열 끝                  회수하다                               # 마지막으로 끈을 돌려줘  끝.  # n자리 문자열을 반환하는 일치 함수  절차. 매치 디짓(n)      일시 정지하다 (v := (많이(&quot;&quot; (&quot;))) & *v <=> n) & v  끝. 

비판

Laurence Tratt는 Icon에 실제 응용 프로그램을 조사하고 우려되는 많은 부분을 지적하는 논문을 작성했습니다.이들 중에는 문자열 처리의 기원에서 파생되었지만 다른 [21]분야에서는 그다지 이치에 맞지 않는 실질적인 결정들이 다수 포함되어 있습니다.그 중:

프로시저의 마지막에 디폴트로 실패하는 결정은 제너레이터의 상황에서는 타당하지만 일반 프로시저의 경우에는 그렇지 않다.위의 예시로 돌아가서write(f(-1))예상대로 출력되지 않습니다.단,[21]

 x := 10  (추가의 줄들)  x := f(-1)  쓰다(x) 

10이 인쇄됩니다.인터랙티브 디버거에서도 아직 모든 코드가 호출되기 때문에 이러한 종류의 문제는 전혀 명백하지 않습니다.x기대치를 채우지 않습니다.이는 프로그래머가 어떤 언어로든 인식해야 하는 '고처' 중 하나로 간주될 수 있지만 Tratt는 다양한 아이콘 프로그램을 조사하여 프로시저의 대부분이 생성기가 아님을 알게 되었습니다.즉,[21] Icon의 기본 동작은 일부 구성 요소에서만 사용되지만 다른 모든 구성 요소에서 잠재적인 오류의 주요 원인이 됩니다.

또 다른 문제는 부울 데이터[b] 유형과 일반적인 부울 로직이 없다는 것입니다.성공/실패 시스템은 값을 확인하는 것이 궁극적인 목표인 대부분의 경우 작동하지만, 단순해 보이는 [22]코드에서 다음과 같은 이상한 동작이 발생할 수 있습니다.

 절차. 주된()     한다면 c 그리고나서 {       쓰다(찍혔다)     }   끝. 

이 프로그램은 "테이크 완료"로 인쇄됩니다.그 이유는 시험이c는 값을 반환합니다.이 값은 제로입니다.그 이외의 모든 미개시 변수에 대한 기본값입니다.0은 유효한 값입니다.if c성공합니다.이를 해결하려면 테스트를 명확하게 해야 합니다.c == 0이는 자가진단 코드를 손상시킵니다.테스트가 "c 제로"인지 "c [22]존재 여부"인지 애매합니다.

「 」를 참조해 주세요.

메모들

  1. ^ fail이 경우는 필요 없습니다.이것은, 의 직전이기 때문입니다.end알기 쉽게 추가되어 있습니다.
  2. ^ 단, Tratt가 지적한 바와 같이 K&R C에는 명시적인 부울 타입이 없으며 false에는 0, [21]true에는 0 이외의 임의의 부울 타입이 사용됩니다.

레퍼런스

인용문

  1. ^ "Update version to 9.5.20i".
  2. ^ Schemenauer, Neil; Peters, Tim; Hetland, Magnus Lie (18 May 2001). "PEP 255 – Simple Generators". Python Enhancement Proposals. Python Software Foundation. Retrieved 9 February 2012.
  3. ^ 그리스월드 1981, 페이지 601, 602
  4. ^ 그리스월드 1981, 페이지 602
  5. ^ 그리스월드 1981, 페이지 606
  6. ^ 그리즈월드 1981, 페이지 608
  7. ^ 그리즈월드 1981, 페이지 609
  8. ^ 그리즈월드 1981, 페이지 629
  9. ^ a b c d e 그리즈월드 & 그리즈월드 1993, 페이지 53
  10. ^ Griswold & Griswold 2002, 페이지 15
  11. ^ 그리즈월드 & 그리즈월드 2002, 페이지 16
  12. ^ Griswold & Griswold 2002, 페이지 10
  13. ^ Griswold & Griswold 2002, 페이지 1
  14. ^ Griswold & Griswold 2002, 페이지 4
  15. ^ a b c d e f Tratt 2010, 74페이지
  16. ^ "Array.prototype.indexOf()". MDN Web Docs.
  17. ^ a b Lane, Rupert (26 July 2015). "SNOBOL - Introduction". Try MTS.
  18. ^ Tratt 2010, 73페이지
  19. ^ a b c 그리즈월드 1996, 2.1페이지
  20. ^ 그리즈월드 1996, 페이지 1
  21. ^ a b c d e f g h Tratt 2010, 75페이지
  22. ^ a b c d Tratt 2010, 76페이지

참고 문헌

외부 링크