Немного изощрений.

Jan 05, 2016 07:16

В самом деле, код на основе массива получается в чём-то проще и гибче: индекс ведь не обязан быть той же разрядности, что и физический адрес, соотв., структуры для хранения этих данных можно сделать меньше. Так и сделал - 16-битный индекс (то есть в массиве не может быть больше 65536 ячеек в принципе, а на самом деле там ещё на один бит меньше, поэтому не более 32768 ячеек). Изменив один #define и перекомпилировав программу, можно сделать 32-битные индексы, соответственно увеличив максимальное количество ячеек до прям таки ниииивааабразимых величин.

Но, подозреваю, однажды выяснится, что одним массивом не обойтись и нужно заводить какую-то параллельную структуру данных для хранения чего-нибудь типа списка (или таблицы) встроенных констанкт, функций и операторов - я не хочу тратить драгоценное ОЗУ контроллера для хранения того, что всё равно не меняется (подобные вещи можно и нужно хранить в памяти программ, всегда).

Пока пишу код мелкими кусочками, отлаживая и исследуя его поведение. Вот, например, обобщённые функции получения данных атома по его индексу и копирования атома:


void* data_of(uclptr_t atom)
{
int type_id = CAR(atom);
int type_valid = (type_id <= TYPES_TOTAL);
return (void*)((type_valid && (UCL_Types[type_id].data != 0)) ? UCL_Types[type_id].data(atom) : 0);
}

uclptr_t copy_atom (uclptr_t original)
{
uclptr_t n = cell_alloc();
if (!IS_NIL(n))
{
int type_id;
int type_valid = ((CAR(n) = (type_id = CAR(original))) <= TYPES_TOTAL);
void *sample_data = (void*)((type_valid && (UCL_Types[type_id].data != 0)) ? UCL_Types[type_id].data(original) : 0);
CDR(n) = (type_valid && (UCL_Types[type_id].create != 0)) ? UCL_Types[type_id].create(sample_data) : NIL;
TAG(n) = TAG_ATOM;
return n;
}
else
{
return NIL;
};
}

Люблю, знаете ли, такой вот вырвиглазный стиль, делающий из старого доброго Си ужасающую мешанину скобок, точек, амперсандов, звёздочек и прочего мусора, за который почему-то не любят простой и прозрачный синтаксис Лиспа.

Простенькая защита от дурака присутствует. Работает, прикольно. Во второй функции можно было бы вставить вызов data_of, но тогда два раза вычислялось бы значение флага type_valid, а зачем мне такие сложности?

uncommon lisp

Previous post Next post
Up