Лайфхаки для ACL программ

1. НАЗВАНИЯ ПРОЦЕДУР. Чтобы обеспечить уникальность названий процедур и одновременно записывать дату их создания разумно ввести такие названия. Первая буква -- год, вторая буква -- месяц, третья -- день, четвертая -- номер процедуры в течение дня. Сами номера можно писать по схеме

  01 02 03 04 05 06 07 08 09 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31
   1  2  3  4  5  6  7  8  9  0  a  b  c  d  e  f  g  h  i  j  k  l  m  n  o  p  q  r  s  t  u

2. ПЕРЕМЕННЫЕ В ПРОЦЕДУРАХ. Так как все переменные являются общими для всех кусков программы и всех процедур, то очень сложно следить за тем -- какие переменные уже заняты и их нельзя использовать. Особенно это касается процедур общего назначения и суперкомманд. Именно это явилось причиной создания объектно ориентированных языков, когда можно вводить переменные внутри процедуры с теми же названиями и они отличаются от переменных с такими же названиями за пределами процедур. В ACL для этой цели можно использовать механизм временного запоминания используемых в процедуре переменных в конце массива r() и восстановления их после того, как процедура закончила свою работу. Как это делать показано на примере написания процедуры вычисления экспоненты от комплексного аргумента на массиве аргументов с постоянным шагом. Вот текст этой процедуры

#pro cexp
# YZ=ZZ-14; #d 9 r(YZ) j n C D a b j1 j2 j3 #v 6 r(YZ-6) j n C D a b !
# j1=j+n; j2=j1+n; j3=j2+n; #ma [op=via; b=j; le=n;] #pas n r(j) r(j2)
#pas n r(j2) r(j3)# C=a; #ma [op=vmc; b=j; le=n;] #ma [op=vex;] #pas n r(j) r(j1)
# C=b; #ma [op=vmc; b=j2; le=n*2;] #ma [op=vco; le=n;] #ma [op=vsi; b=j3;]
#ma [op=vvm; b=j; trx=n*2;] #ma [b=j1;] #ma [op=mtr; b=j; nx=n; ny=2;]
#v 9 r(YZ) j n C D a b j1 j2 j3
@

Как это работает? Процедура вычисляет exp((a+ib)*x), x=C+i*D, i=0,...,n-1. Аргументами являются 6 переменных: j -- начальный индекс массива r(), где будет записан ответ, n -- число точек массива, C -- начальное значение переменной х, D -- шаг изменения переменной х, a -- реальная часть коэффициента, b -- мнимая часть коэффициента. Удобно в любой программе с самого начала определить переменную ZZ=s(109); То есть она равна размеру массива r(). В разных версиях интерпретатора этот массив может иметь разный размер, но его всегда можно узнать таким способом. Выделяем 20 значений в конце массива. Там перед вызовом сначала будут аргументы процедуры, а затем туда же надо записать старые значения всех переменных, которые будут использованы в процедуре, причем сначала снова аргументы, так как они как раз изменятся в первую очередь.

Так вычитая 6 из 20 получаем 14, определяем индекс YZ и по команде #d запоминаем все значения переменных, которые используются в процедуре. В примере их 9, но может быть сколько угодно. Если их будет больше, то выделяем не 20, а 30 или еще больше значений в конце массива r(). Затем по команде #v делаем обратную операцию, то есть вынимаем из конца массива r() аргументы процедуры. После этого пишем текст самой процедуры с теми переменными, названия которых нам наиболее удобны. А в конце снова повторяем весь список команды #d заменяя ее на #v. При этом все переменные, которые были испорчены получают свои исходные значения. То есть процедура написана в привычных обозначениях, но она не испортила значений, которые были там до вызова процедуры.

Удобство такой техники еще и в том, что при вызове данной процедуры можно использовать разные (и другие) переменные. Вот пример вызова

#d 6 r(ZZ-20) J N x0 x1 A B #e _cexp

Такая техника полностью реализует как аппарат формальных переменных процедуры, так и аппарат локальных переменных. С другой стороны, это всего лишь один способ из многих. И нет никакой необходимости скрывать пересылки, которые в других языках тоже выполняются, только программист этого не видит. В языке Java это делается особенно затратно, если пользоваться такими методами. Интерпретатор, разумеется тоже их использует, но наличие большого массива все же уменьшает мусор.

.

  Внимание! Сайт оптимизирован под браузер Google Chrome.