2010-07-13 3 views
10
Program ConstTest; 
    Const constVar = 1; 
    Begin 
    constVar := 3; 
    WriteLn(constVar); 
    End. 

Совершенно очевидно, что приведенный выше код не будет компилироваться, потому что неправильно изменять значение константы. Однако следующий код компилируется, и возвращает «1; 5; 3;», даже если массив является константным:Почему массивы Pascal const на самом деле не являются константами?

Program ConstTest; 
    Const constArr:Array [1..3] Of ShortInt = (1,2,3); 
    Var i:ShortInt; 
    Begin 
    constArr[2] := 5; 
    For i:=1 To 3 Do WriteLn(constArr[i],'; '); 
    End. 

Итак, что вызывает такое поведение? Почему константа на самом деле не постоянна?

Я использую FreePascal Compiler 2.2.0 для Win32.

+0

См. Также http://stackoverflow.com/questions/48934/in-delphi-7-why-can-i-assign-a-value-to-a-const и http://stackoverflow.com/questions/2714365/Дельфи-все-константы-являются постоянной но-некоторых-это-более постоянной, чем другие. –

ответ

11

У вас есть типизированная константа. Типированные константы отличаются от обычных констант (a.k.a. истинные константы), что является вашим constVar. Обратите внимание, как вам не нужно было указывать тип на constVar; если у вас, вы можете увидеть, что компилятор позволяет присвоенных новые значения к нему тоже:

const 
    constVar: Integer = 1; 

The Free Pascal manual описывает типизированные константы:

В отличие от обычных констант, значения могут быть назначены их во время выполнения. Это старая концепция от Turbo Pascal, которая была заменена поддержкой инициализированных переменных: Подробное описание см. В разделе 4.4, стр. 183.

Поддержка присвоения значений типизированным константам управляется директивой {$J}: ее можно отключить, но по умолчанию (для совместимости с Turbo Pascal). Инициализированные переменные всегда разрешены.

Для инициализированной переменной замените const на var в вашей декларации. Он получит свою ценность при вводе области. Или, выключите $J директиву до набранного-объявления константы:

{$J-} 
const 
    constArr: array [1..3] of ShortInt = (1, 2, 3); 
{$J+} 

ли вы превратить его обратно на потом до вас.


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

0

Ну, если вы знаете, C, вот несколько аналогий:

В [Turbo/Free] Pascal, писать что-то вроде этого:

const 
    MIN = 5; 
    MAX = 10; 

эквивалентно делать это в C:

#define MIN 5 
#define MAX 10 

То есть, это символ времени компиляции, как и другие плакаты.

С записями и массивами (типизированные константы) выражение «const» является способом инициализации блока памяти, связанного с символом линкера.

TODO: счетчик пример.

Смежные вопросы