Pragmas
Pragmas
코드에서 '이 파일은 Raku 6.c 버전으로 돌려줘' 같은 요구를 하거나, 컴파일러의 기본 동작을 그때그때 바꾸고 싶을 때가 있어요. Raku에서 pragma는 사용할 Raku의 특정 버전을 지정하거나 컴파일러의 정상 동작을 어떤 방식으로든 수정하는 지시문이에요.
본문
Raku에서 pragma는 사용할 Raku의 특정 버전을 식별하거나 컴파일러의 정상 동작을 어떤 방식으로든 수정하는 지시문이에요. use 키워드가 pragma를 활성화해요 (모듈을 use하는 것과 비슷해요). pragma를 비활성화하려면 no 키워드를 써요:
use v6.c; # 6.c 언어 버전 사용
no worries; # 컴파일 시간 경고를 내지 않기
다음은 각 pragma의 목적에 대한 짧은 설명 또는 사용법에 대한 더 자세한 링크와 함께 나열한 pragma 목록이에요.
v6.x
이 pragma는 사용할 컴파일러 버전을 명시하고, 그 기능이 선택적이면 켜요.
이 pragma들은 컴파일러 버전을 켜기 때문에 파일의 첫 번째 문장이어야 해요 (앞의 주석과 Pod는 괜찮아요).
use v6; # 지원되는 최신 버전(비-PREVIEW) 로드
역사적으로 use v6;는 Perl 인터프리터에게 오류를 내고 사용자에게 Perl 6을 쓰라고 경고하라는 신호를 주기 위한 것이었어요. 더 이상 그런 고려는 없으므로 이 문장은 이제 의미가 없어졌어요.
use v6.c; # "Christmas" 버전의 Raku 사용
use v6.d; # "Diwali" 버전의 Raku 사용
6.d를 구현한 2018.11부터 이 pragma는 아무것도 하지 않아요.
use v6.d.PREVIEW; # 6.d 지원 컴파일러에서는 6.d 기능 활성화,
# 그렇지 않으면 6.d 언어의 사용 가능한 실험적
# 프리뷰 기능 활성화
use v6.e.PREVIEW; # 6.e 언어의 사용 가능한 실험적 프리뷰 기능 활성화
use v6.*; # 현재 개발 중인 언어 버전의 사용 가능한 실험적
# 프리뷰 기능 활성화
MONKEY-GUTS
use MONKEY-GUTS;
이 pragma는 현재 어떤 Raku 명세의 일부가 아니지만, Rakudo에서 use nqp의 동의어로 존재해요 (아래 참고).
MONKEY-SEE-NO-EVAL
use EVAL;
위험성 때문에 그렇지 않으면 컴파일러 오류를 일으키는 EVAL 루틴의 사용을 활성화해요. 자세한 내용은 <EVAL 루틴>을 보세요.
루틴과 달리 객체의 EVAL 메서드는 이 pragma 없이도 실행될 수 있다는 점에 주의하세요. 즉 MONKEY pragma가 없다고 해서 EVAL 호출을 막아주는 보장은 아니에요.
MONKEY-TYPING
use MONKEY-TYPING;
기존 클래스와 그라마에 (속성은 아니고) 메서드를 추가하는 augment를 활성화해요.
MONKEY
use MONKEY;
사용 가능한 모든 MONKEY pragma를 켜요. 다음과 동등해요:
use MONKEY-TYPING;
use MONKEY-SEE-NO-EVAL;
use MONKEY-GUTS;
dynamic-scope
pragma의 어휘 스코프에 있는 변수에 is dynamic 트레잇을 적용해요. 효과는 인자로 변수 이름을 나열하면 변수들의 부분집합으로 제한할 수 있어요. 기본적으로 모든 변수에 적용해요.
# `is dynamic`을 $x에만 적용하고 $y에는 적용하지 않기
use dynamic-scope <$x>;
sub poke {
say $CALLER::x;
say $CALLER::y;
}
my $x = 23;
my $y = 34;
poke;
# OUTPUT:
# 23
# Cannot access '$y' through CALLER, because it is not declared as dynamic
이 pragma는 현재 어떤 Raku 명세의 일부가 아니며 Rakudo 2019.03에서 추가됐어요.
experimental
<실험적 기능>의 사용을 허용해요.
fatal
루틴이 반환하는 +를 쓰면 say $x.^name; 줄에 도달해서 출력에
두 번째 블록에서는 use fatal pragma가 활성화되어 있어서, 접두 +가 반환한 CATCH 블록이 실행되어 Caught... 줄을 출력하므로 say 줄에 절대 도달하지 않아요. 두 블록 모두 같은 프로그램이고 use fatal이 자신이 사용된 어휘 블록에만 영향을 준다는 점에 주의하세요:
{
my $x = +"a";
say $x.^name;
CATCH { default { say "Caught {.^name}" } }
} # OUTPUT: «Failure»
{
use fatal;
my $x = +"a";
say $x.^name;
CATCH { default { say "Caught {.^name}" } }
} # OUTPUT: «Caught X::Str::Numeric»
<try 블록> 안에서는 fatal pragma가 기본적으로 활성화되고, no fatal로 비활성화할 수 있어요:
try {
my $x = +"a";
say $x.^name;
CATCH { default { say "Caught {.^name}" } }
} # OUTPUT: «Caught X::Str::Numeric»
try {
no fatal;
my $x = +"a";
say $x.^name;
CATCH { default { say "Caught {.^name}" } }
} # OUTPUT: «Failure»
isms
[2018.09 이상]
일반적인 Raku 프로그래밍에서 함정으로 여겨져 경고 및/또는 오류를 정당화했던 다른 언어 구문 일부를 허용해요. 현재 Perl과 C++가 허용돼요.
sub abs() { say "foo" }
abs;
# Unsupported use of bare "abs"; in Raku please use .abs if you meant
# to call it as a method on $_, or use an explicit invocant or argument,
# or use &abs to refer to the function as a noun
이 경우 인자를 받지 않는 abs sub를 제공해도 컴파일 오류가 사라지지 않았어요.
use isms <Perl5>;
sub abs() { say "foo" }
abs; # foo
이렇게 하면 컴파일러가 문제의 Perl 구문을 허용해서 코드가 실제로 실행되게 해요. 언어를 지정하지 않으면 알려진 모든 언어 구문이 허용돼요.
use isms; # Perl과 C++ isms 허용
lib
이 pragma는 인터프리터가 <모듈을 찾을> 수 있도록 라이브러리 검색 경로에 하위 디렉터리를 추가해요.
use lib <lib /opt/lib /usr/local/lib>;
#또는 IO::Path와 Str의 혼합 리스트
use lib ('.', '.'.IO, './lib'.IO);
이것은 리스트로 전달한 디렉터리를 검색할 거예요. 더 많은 예는 <모듈 문서>를 확인하세요.
newline
호출된 스코프에서 $?NL 상수의 값을 설정해요. 가능한 값은 :lf(기본값, Line Feed를 나타냄), :crlf(Carriage Return, Line Feed), :cr(Carriage Return)이에요.
nqp
스스로 위험을 감수하고 쓰세요.
이것은 Rakudo 특유의 pragma예요. 이것을 사용하면 Rakudo가
use nqp;
nqp::say("hello world");
이것은 Raku 루틴 대신 기반 nqp say opcode를 사용해요. 이 pragma는 코드를 특정 nqp 버전에 의존하게 할 수 있는데, 그 코드는 Raku 명세의 일부가 아니므로 안정적이 보장되지 않아요. Rakudo 코어에는 코어 기능을 가능한 한 빠르게 만들기 위해 사용하는 많은 사용처를 찾을 수 있어요. Rakudo의 향후 코드 생성 최적화가 이런 사용처를 구식으로 만들 수 있어요.
precompilation
기본값은 소스 코드의 프리컴파일을 허용하는데, 특히 모듈에서 사용될 때 그래요. 어떤 이유로든 (모듈의) 코드가 프리컴파일되길 원하지 않으면 no precompilation을 쓸 수 있어요. 이렇게 하면 전체 컴파일 유닛(보통 파일)이 프리컴파일되지 않도록 막아요.
soft
strict
strict는 기본 동작이며, 변수를 사용하기 전에 선언할 것을 요구해요. 이 제한을 no로 완화할 수 있어요.
no strict; $x = 42; # OK
trace
use trace가 활성화되면 실행되는 모든 코드 줄이 STDERR에 기록돼요. no trace로 이 기능을 꺼서 특정 코드 섹션에서만 이런 일이 발생하게 할 수 있어요.
v6
<테스트 작성> 관련.
variables
<정의된 변수 pragma> 관련.
worries
컴파일러가 생성한 컴파일 시간 경고가 표시될지 여부를 어휘적으로 제어해요. 기본적으로 활성화돼요.
$ raku -e 'say :foo<>.Pair'
Potential difficulties:
Pair with <> really means an empty list, not null string; use :foo('') to represent the null string,
or :foo() to represent the empty list more accurately
at -e:1
------> say :foo<>⏏.Pair
foo => Nil
$ raku -e 'no worries; say :foo<>.Pair'
foo => Nil