COBOL добавляет 0 к переменной в COMPUTE - PullRequest
3 голосов
/ 15 декабря 2011

Я столкнулся со странным утверждением при работе над программой на языке COBOL из $ WORK.

У нас есть параграф, который открывает курсор (из DB2) и циклически повторяет его, пока он не достигнет EOT (в псевдокоде):

... working storage ...
01  I                       PIC S9(9) COMP VALUE ZEROS.
01  WS-SUB                  PIC S9(4) COMP VALUE 0.

... code area ...
PARA-ONE.                                                
    PERFORM OPEN-CURSOR
    PERFORM FETCH-CURSOR

    PERFORM VARYING I FROM 1 BY 1 UNTIL SQLCODE = DB2EOT                        
        do stuff here...
    END-PERFORM                                           

    COMPUTE WS-SUB = I + 0                            
    PERFORM CLOSE-CURSOR

    ... do another loop using WS-SUB ...

Мне интересно, почему эта линия COMPUTE WS-SUB = I + 0 есть. Насколько я понимаю, I всегда будет, по крайней мере, 1 из-за блока выполнения над ним (т. Е. Даже если для начала есть EOT, I будет установлен в единицу на этой начальной итерации).

Эта COMPUTE линия вообще нужна? Это некое неявное приведение, о котором я не знаю? Зачем это там? Почему бы тебе не просто MOVE I TO WS-SUB?

Ответы [ 3 ]

6 голосов
/ 15 декабря 2011

Называть это глупо, но с некоторыми компиляторами (с правильными действующими параметрами), учитывая, что

 01  SIGNED-NUMBER   PIC S99 COMP-5 VALUE -1.
 01  UNSIGNED-NUMBER PIC  99 COMP-5.
      ... 
      MOVE SIGNED-NUMBER TO UNSIGNED-NUMBER
      DISPLAY UNSIGNED-NUMBER

приводит к: 255. Но ...

COMPUTE UNSIGNED-NUMBER = SIGNED-NUMBER + ZERO

приводит к: 1 (без знака)

Таким образом, чтобы ответить на ваш вопрос, это можно классифицировать как метод, использующий приведение чисел со знаком в числа без знака.Однако в приведенном вами примере кода это не имеет никакого смысла.

0 голосов
/ 22 января 2013

Интересно, была ли когда-нибудь тестовая версия источников

COMPUTE WS-SUB = I + 0
    ON SIZE ERROR
        DISPLAY "WS-SUB overflow"
        STOP RUN
END-COMPUTE

с тестом диапазона, от которого отказались, когда разработчик был удовлетворен и вычищен? MOVE не допускает декларативных операторов размера. Это так много причин, как я мог видеть. Или, может быть, привычка разработчика использовать COMPUTE для перемещения, в качестве тонкого напоминания о необходимости защищать код на каждом этапе? И, возможно, не зная, как указал Джо, предложение SIZE было бы столь же эффективным без + 0? Или сопровождающий боролся с отключением одной ошибки, и после тестирования произошли корректирующие изменения с 1 на 0?

0 голосов
/ 21 января 2013

Обратите внимание, что определение «I» (вероятно) было закодировано одним программистом, а WS-SUB - другим (именование отличается, предложение VALUE отличается для той же цели).

Программист 2 выглядит так«старая школа»: PIC S9 (4), подписано и занято все цифры, которые «вписываются» в одно слово.S9 (9), вероятно, «намного выше» по диапазону возможных значений, но такие вещи совсем не касаются Программиста 1.

Возможно, Программист 2 беспокоился об использовании COMP для S9 (9) длячто-то, требующее (возможно, много) меньше, чем 9999 «вещей».«Я буду« эффективен », не меняя существующий код».Мне кажется маловероятным, что поле когда-либо было определено как беззнаковое.

COMP / COMP-4 с девятью цифрами действительно снижает производительность при использовании для расчетов.Попробуйте «ДОБАВИТЬ 1» к 9 (9) и 9 (8) и 9 (10) и сравните сгенерированный код.Если у вас может быть девять цифр, определите с помощью 9 (10), в противном случае 9 (8), если вам нужно полное слово.

Программист 2 знает что-то об этом.

КОМПЬЮТЕР с + 0вероятно преднамеренно.Почему Программист 2 использовал COMPUTE таким образом (исходный вопрос)?

Теперь это будет усложнено.

На Мэйнфрейме есть два «типа» «двоичных» полей:те, которые будут содержать значения, ограниченные предложением PICture (USAGE BINARY, COMP и COMP-4);те, которые содержат значения, ограниченные размером поля (USAGE COMP-5).

В BINARY / COMP / COMP-4 размер поля определяется из PICture, как и значения, которые можно удерживать.PIC 9 (4) - это полуслово, максимальное значение которого равно 9999. PIC S9 (4) - полуслово со значениями от -9999 до + 9999.

С COMP-5 (Native Binary), PICture просто определяетРазмер поля, все биты поля имеют отношение к значению поля.PIC 9 (1) - 9 (4) определяют полуслова, рис. 9 (5) - 9 (9) определяют полные слова, а 9 (10) - 9 (18) определяют двойные слова.PIC 9 (1) может содержать максимум 65535, S9 (1) от -32 768 до + 32 767.

Все хорошо.Тогда есть опция компилятора TRUNC.Это имеет три варианта.STD, значение по умолчанию, BIN и OPT.

BIN можно считать наиболее далеко идущим.BIN заставляет BINARY / COMP / COMP-4 вести себя как COMP-5.По сути, все становится COMP-5.PICtures для двоичных полей игнорируется, за исключением определения размера поля (и, что любопытно, с помощью ON SIZE ERROR, которая «ошибается», когда превышаются максимумы в соответствии с PICture).Native Binary в IBM Enterprise Cobol генерирует в основном, хотя и не исключительно, «самый медленный» код.Усечение соответствует размеру поля (полслово, полное слово, двойное слово).

STD, по умолчанию используется "стандартное" усечение.Это усекает до "PICture".Поэтому это «десятичное» усечение.

OPT для «производительности».С OPT компилятор усекается любым способом, который наиболее «эффективен» для конкретной «кодовой последовательности».Это может означать, что промежуточные значения и конечные значения могут иметь «установленные биты», которые находятся «вне диапазона» PICture.Однако при использовании в качестве источника двоичное поле всегда будет отражать только значение, указанное в PICture, даже если установлены «избыточные» биты.

При использовании OPT важно, чтобы все двоичные поля «соответствовали».to PICture »означает, что код никогда не должен полагаться на биты, которые установлены вне определения PICture.

Примечание. Даже если OPT был использован, OPTimizer (OPT (STD) или OPT (FULL)) все еще может обеспечитьдальнейшая оптимизация.

Это все хорошо.

Однако, "pickle" может легко возникнуть, если вы "смешаете" опции TRUNC, или если двоичное определение в программе CALLing не являетсятак же, как в вызываемой программе.«Смешение» может произойти, если модули в одном и том же модуле выполнения скомпилированы с различными параметрами TRUNC или если двоичное поле в файле записано с одним параметром TRUNC, а затем прочитано с другим.

Теперь, я подозреваю, что Программист 2 столкнулся с чем-то вроде этого: либо с помощью TRUNC (OPT) они заметили «лишние биты» в поле и подумали, что с ними нужно иметь дело, либо через «сочетание» опций в модуле выполнения или «при использовании файла» они замечали «лишние биты», когда необходимо было что-то с этим сделать (то есть «удалить смесь»).

Программист 2 разработал КОМПЬЮТЕР A = B + 0, чтобы «справиться» с конкретной проблемой (предполагаемой или реальной), а затем применил ее в целом к ​​своей работе.

Это «догадка», или, лучше, «рационализация», которая работает с известной информацией.

Это "поддельное" исправление. Либо не было никаких проблем (нормальный способ работы TRUNC (OPT)), либо правильным разрешением было «нормализация» опции TRUNC для модулей / файлов.

Я не хочу, чтобы людей, спешащих сейчас, бросились и вставили COMPUTE A = B + 0 в свой код. Для начала, они не знают, почему они это делают. Для продолжения это неправильная вещь, которую нужно сделать.

Конечно, не , просто удалите «+ 0» из любого из них, которые вы найдете. Если есть «смесь» TRUNC, программа может перестать «работать».

В одной ситуации я использовал «ADD ZERO» для BINARY / COMP / COMP-4. Это в программе "Микки Маус", программе, не имеющей цели, кроме как попробовать что-то. Здесь я использовал его как метод, чтобы «обмануть» оптимизатор, так как в противном случае оптимизатор мог бы видеть неизменяемые значения, поэтому генерировал бы код для использования буквальных результатов, поскольку все значения были известны во время компиляции. (Возможно, «более аккуратный» и более гибкий способ сделать это, который я взял в PhilinOxford, - это использовать ACCEPT для поля). Наверное, дело обстоит не так с рассматриваемым кодом.

...