Forth и другие саморасширяющиеся системы программирования Locations of visitors to this page
Текущее время: Ср апр 24, 2024 13:08

...
Google Search
Forth-FAQ Spy Grafic

Часовой пояс: UTC + 3 часа [ Летнее время ]




Начать новую тему Ответить на тему  [ Сообщений: 3 ] 
Автор Сообщение
 Заголовок сообщения: CASE
СообщениеДобавлено: Пн дек 03, 2007 05:04 
Не в сети
Moderator
Moderator
Аватара пользователя

Зарегистрирован: Чт май 04, 2006 00:53
Сообщения: 5062
Откуда: был Крым, теперь Новосибирск
Благодарил (а): 23 раз.
Поблагодарили: 63 раз.
У стандартной структуры CASE OF ENDOF ENDCASE есть неприятная особенность, которая заключается в том, что OF всегда сравнивает значение на равенство с константой. В предлогаемой библиотечке эта неудобность исправлена, и можно делать так:
<pre>
: sample CASE 1 = uOF ." понедельник " ENDOF
2 OF ." вторник " ENDOF
3 = uOF ." среда " ENDOF
5 < uOF ." четверг или пятница " ENDOF
." другой "
ENDCASE ." недели день" CR ;

2 sample
4 sample
</pre>
Кроме того совсем не обязательно создавать слово, если вам необходимо сделать выбор всего один раз, да еще и во время компиляции кода. Поэтому сейчас можно делать и так:
<pre>
3 CASE 1 = uOF ." понедельник " ENDOF
2 = uOF ." вторник " ENDOF
3 = uOF ." среда " ENDOF
5 < uOF ." четверг или пятница " ENDOF
." другой "
ENDCASE
</pre>
Код:
\ 02-12-2007 ~mOleg
\ Copyright [C] 2007 mOleg mininoleg@yahoo.com
\ Конструкция выбора CASE
\ с учетом возможной вложенности операторов CASE
\ с возможностью исполнения во время интерпретации

REQUIRE WHILENOT    devel\~moleg\lib\util\ifnot.f
REQUIRE COMPILE     devel\~moleg\lib\util\compile.f
REQUIRE CS>         devel\~moleg\lib\util\csp.f
REQUIRE controls    devel\~moleg\lib\util\run.f

\ начать описание выбора варианта
: CASE ( n --> )
        STATE @ IFNOT init: THEN 5 controls +!
        !CSP COMPILE DUP ; IMMEDIATE

\ в отличие от OF данный вариант не сам сравнивает число,
\ а лишь получает флаг. Сравнение производится перед uOF
\ см примеры в конце
: uOF ( flag --> )
      COMPILE OVER COMPILE SWAP [COMPILE] IF COMPILE 2DROP ; IMMEDIATE

\ если n = значению, переданному CASE выполнить код вплодь то ENDOF
\ иначе пропустить секцию
: OF ( n --> ) COMPILE = [COMPILE] uOF ; IMMEDIATE

\ завершить описание варианта, начатого OF или uOF
: ENDOF ( --> ) [COMPILE] ELSE ; IMMEDIATE

\ завершить конструкцию CASE
: ENDCASE ( n n --> )
          ?COMP -5 controls +!
          COMPILE NIP COMPILE NIP
          BEGIN ?CSP WHILE [COMPILE] THEN REPEAT CSDrop
          controls @ IFNOT [COMPILE] ;stop THEN ; IMMEDIATE

?DEFINED test{ \EOF -- тестовая секция ---------------------------------------

test{ 3 CASE  0 OF 123456 ENDOF
              1 OF 092874 ENDOF
              2 = uOF 569871 ENDOF
              3 = uOF 576948 ENDOF
              4 OF 689299 ENDOF
              234234
         ENDCASE 576948 <> THROW

     : sample CASE  0 OF 123456 ENDOF
                    0 OF 092874 ENDOF
                    2 = uOF 569871 ENDOF
                    3 = uOF 576948 ENDOF
                    4 OF 689299 ENDOF
                   234234
              ENDCASE ;
     0 sample 123456 <> THROW
     1 sample 234234 <> THROW
     2 sample 569871 <> THROW

     \ проверка на вложенность
     2 CASE 2 OF 48570
                 CASE 48570 = uOF 0 ENDOF
                      -1
                 ENDCASE
              ENDOF
            -1
       ENDCASE THROW

  S" passed" TYPE
}test


и нужна будет еще такая либа:
Код:
<csp.f >

\ 02-12-2007 ~mOleg
\ Copyright [C] 2007 mOleg mininoleg@yahoo.com
\ стек управления компиляцией

REQUIRE NewStack  devel\~mOleg\lib\util\stack.f

VOCABULARY C-Stack
           ALSO C-Stack DEFINITIONS

        USER-VALUE CStack  \ CSP

    100 CONSTANT #CS       \ предельная глубина стека CS

\ вернуть CSid
: CSP ( --> addr ) CStack DUP IF ELSE DROP #CS NewStack DUP TO CStack THEN ;

ALSO FORTH DEFINITIONS

\ переместить число на вершину стека CS
: >CS ( u --> ) CSP PushTo ;

\ снять число с вершины стека CS
: CS> ( --> u ) CSP PopFrom ;

\ прочитать число с вершины стека SC
: CS@ ( --> u ) CSP ReadTop ;

\ удалить верхнее значение с вершины CS

: CSDrop ( cs: u --> ) CSP DropTop ;

\ снять с CS #-тое значение
: CSPick ( # --> u ) CSP PickFrom ;

\ определить глубину CS
: CSDepth ( --> # ) CSP StackDepth ;

\ сохранить текущее состояние SP в CS
: !CSP ( --> ) SP@ >CS ;

\ проверить сбалансирован ли стек
: ?CSP ( -> flag ) SP@ CS@ <> ;

PREVIOUS PREVIOUS DEFINITIONS

?DEFINED test{ \EOF -- Тестовая секцияґ ---------------------------------------
        CSDepth 0 <> THROW
        123 >CS CS@ 123 <> THROW
        234 >CS CS@ 234 <> THROW
        345 >CS 2 CSPick 123 <> THROW
        CSDepth 3 = 0= THROW
        CS> 345 = 0= THROW
        CS> 234 = 0= THROW
        CS> 123 = 0= THROW
        !CSP SP@ CS@ <> THROW
        ?CSP THROW
  S" passed" TYPE
}test


_________________
Мне бы только мой крошечный вклад внести,
За короткую жизнь сплести
Хотя бы ниточку шёлка.
fleur


Вернуться к началу
 Профиль Отправить личное сообщение  
Ответить с цитатой  
 Заголовок сообщения:
СообщениеДобавлено: Пн дек 03, 2007 07:01 
---


Последний раз редактировалось profiT Пт фев 29, 2008 23:58, всего редактировалось 1 раз.

Вернуться к началу
  
Ответить с цитатой  
 Заголовок сообщения:
СообщениеДобавлено: Пн дек 03, 2007 07:28 
Не в сети
Moderator
Moderator
Аватара пользователя

Зарегистрирован: Чт май 04, 2006 00:53
Сообщения: 5062
Откуда: был Крым, теперь Новосибирск
Благодарил (а): 23 раз.
Поблагодарили: 63 раз.
profiT писал(а):
~yz/lib/mycase.f

неа 8)

profiT писал(а):
Почему не стоит запоминать глубину стека компилятора

логично, но даже lib\ext\case.f, что идет в стандартном СПФе болеет той же проблемой.
да и проблема ли это?

_________________
Мне бы только мой крошечный вклад внести,
За короткую жизнь сплести
Хотя бы ниточку шёлка.
fleur


Вернуться к началу
 Профиль Отправить личное сообщение  
Ответить с цитатой  
Показать сообщения за:  Поле сортировки  
Начать новую тему Ответить на тему  [ Сообщений: 3 ] 

Часовой пояс: UTC + 3 часа [ Летнее время ]


Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и гости: 5


Вы не можете начинать темы
Вы можете отвечать на сообщения
Вы не можете редактировать свои сообщения
Вы не можете удалять свои сообщения
Вы не можете добавлять вложения

Powered by phpBB © 2000, 2002, 2005, 2007 phpBB Group
phpBB сборка от FladeX // Русская поддержка phpBB