табличные методы
От: Jandor Россия  
Дата: 25.11.05 01:36
Оценка:
Всем привет.
Человек я здесь новый, так что строго не судите
Сам я пишу на Дельфи, поэтому на нее и ориентируюсь.
Понятно, что если в языках давно есть указатель на функцию/процедуру, то не мне первому эта идея в голову пришла. Мне неясно только, почему реализацию этой идеи я практически не встречаю. Может, плохо смотрю?

Сложную логику (вложенные if'ы), реузьтатом которых является присвоение чего-либо одной переменной, можно схлопнуть в const массив и обращаться к его элементам, используя как индекс само условие (благо, в Дельфи индекс массива пожет иметь любой перечислимый тип, в том числе и Boolean).
Возможно, что нужно будет использовать хеш-функцию для отображения "условий" на индекс массива.
Const-массив указателей на функции дает нам "дешевый" полиморфизм.
Вообще индексация схожих по смыслу вещей (ответов, действий, полей записи — пример поля TRect и TPoint...) дает основу для нехилого обобщения и уменьшения (!) кода, чем я сам регулярно пользуюсь.

Вот... вообще я это уже нашел в Code Complete под названием "Табличные методы", но там далеко не все, что у меня сейчас в голове роится.

Всем спасибо за внимание!

P.S. Наверное, это меня haskell испортил
[yellow leaf]
Re: табличные методы
От: beroal Украина  
Дата: 25.11.05 09:16
Оценка:
Здравствуйте, Jandor, Вы писали:
J>Понятно, что если в языках давно есть указатель на функцию/процедуру, то не мне первому эта идея в голову пришла. Мне неясно только, почему реализацию этой идеи я практически не встречаю. Может, плохо смотрю?
J>Сложную логику (вложенные if'ы), реузьтатом которых является присвоение чего-либо одной переменной, можно схлопнуть в const массив и обращаться к его элементам, используя как индекс само условие (благо, в Дельфи индекс массива пожет иметь любой перечислимый тип, в том числе и Boolean).
J>Const-массив указателей на функции дает нам "дешевый" полиморфизм.
Если не изменяет память, именно так устроена (или раньше была устроена) обработка конструкции case в GHC runtime system.
Re: табличные методы
От: Сергей Губанов Россия http://sergey-gubanov.livejournal.com/
Дата: 25.11.05 10:05
Оценка:
Здравствуйте, Jandor, Вы писали:

J>Const-массив указателей на функции дает нам "дешевый" полиморфизм.


Я так (на Component Pascal) синтаксический анализатор писал. Массив из процедур, а индекс — номер буквы, на которую начинается слово. Дёшево и сердито.

Re[2]: табличные методы
От: gear nuke  
Дата: 25.11.05 11:27
Оценка:
Здравствуйте, Сергей Губанов, Вы писали:

J>>Const-массив указателей на функции дает нам "дешевый" полиморфизм.


СГ>Я так (на Component Pascal) синтаксический анализатор писал. Массив из процедур, а индекс — номер буквы, на которую начинается слово. Дёшево и сердито.


СГ>


ИМХО такие вещи должен оптимизатор делать сам, а нам для него должно быть достаточно просто написать switch. Тогда будет меньше проблем с сопровождением. Что радует, бывает оптимизаторы так и делают.

Хотя не всегда. Не 64 мегабайта же таблицу делать для такого:
    /// Конвертиреут знаки операций из ASCII во внутреннее представление.
    Lexem static inline lexem(const tree_chars val)
    {
        const unsigned v = reinterpret_cast<unsigned>(val);
        switch ( v )
        {
        case '*>-':     return arrow_asterisk;          //  ->*
        case '...':     return dot_dot_dot;             //  ...
        case '=>>':     return greater_greater_equal;   //  >>=
        case '=<<':     return less_less_equal;         //  <<=
        default: switch ( static_cast<two_chars>(v) )
            {
            case '&&':  return ampersand_ampersand;     //  &&
            case '=&':  return ampersand_equal;         //  &=
            case '>-':  return arrow;                   //  ->
            case '=*':  return asterisk_equal;          //  *=
            case '=^':  return caret_equal;             //  ^=
            case '::':  return colon_colon;             //  ::
            case '*.':  return dot_asterisk;            //  .*
            case '==':  return equal_equal;             //  ==
            case '=>':  return greater_equal;           //  >=
            case '>>':  return greater_greater;         //  >>
            case '=<':  return less_equal;              //  <=
            case '<<':  return less_less;               //  <<
            case '=-':  return minus_equal;             //  -=
            case '--':  return minus_minus;             //  --
            case '=!':  return non_equal;               //  !=
            case '=%':  return percent_equal;           //  %=
            case '=+':  return plus_equal;              //  +=
            case '++':  return plus_plus;               //  ++
            case '=/':  return slash_equal;             //  /=
            case '=|':  return vertical_equal;          //  |=
            case '||':  return vertical_vertical;       //  ||
            default:    return static_cast<Lexem>(static_cast<byte_t>(v));
        }   }
    }

А вообще, этот "трюк с таблицами" давно известен на ассемблере. Забавно, что и на HLL его не забыли.
People who are more than casually interested in computers should have at least some idea of what the underlying hardware is like. Otherwise the programs they write will be pretty weird (c) D.Knuth
Re: табличные методы
От: jazzer Россия Skype: enerjazzer
Дата: 28.11.05 01:40
Оценка:
Здравствуйте, Jandor, Вы писали:

J>Вот... вообще я это уже нашел в Code Complete под названием "Табличные методы", но там далеко не все, что у меня сейчас в голове роится.


Одна из реализаций мультиметодов на С++ как раз работает на таблицах
jazzer (Skype: enerjazzer) Ночная тема для RSDN
Автор: jazzer
Дата: 26.11.09

You will always get what you always got
  If you always do  what you always did
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.