Ошибки PascalABC.NET


#1492

Извиняюсь заранее, если уже и так это знаете. На всякий случай. Visual Studio 2017 Community бесплатен если меньше 100 компьютеров и доход от его использования меньше 1 миллиона долларов в год (цифры мог немного переврать, но порядок тот). Надо просто форму заполнить и будет официальная лицензия. Я так и работаю. Инсталлятор у него более щадящий, чем предыдущие версии, кучу лишнего не ставит. Проект PascalABC.NET на github достаточно аккуратно сделан, так что после подключения к нему этой VS Community Вы можете спокойно компилировать, даже вносить какие-нибудь мелкие исправления.


#1495

Ошибка: Нельзя преобразовать тип real к integer

begin
  var a := 10;
  var b: real;  
  b := a < 5 ? a * 2 : a / 2;  //в этой строке
  b.Print
end.

а если с условным оператором то работает

if a < 5 then b := 2 * a
else b := a / 2;

и так тоже работает

b := a >= 5 ? a / 2 : a * 2;

#1496

Похоже, действительно баг, заводится какая-то внутренняя переменная, тип которой определяется типом выражения, стоящего после ?, а потом вычисленное выражение преобразуется к этому типу и выдается в качестве значения правой части оператора присваивания.

Вот так работает: b := a < 5 ? a * 2.0 : a / 2;


#1497

Нет, это не баг. Тип выражения ? : определяется по типу первого выражения, а оно - integer


#1498

Это в паскале абц или в других языках программирования тоже? В C# нашел такое: %D0%A1%D0%BD%D0%B8%D0%BC%D0%BE%D0%BA


#1500

Тогда это бомбочка, которую очень легко себе подложить. Ибо как НИГДЕ НЕ СКАЗАНО про то, что “Тип выражения ? : определяется по типу первого выражения,” Быть может, это надо как-то в Справке упомянуть?


#1501

А что делать если слева и справа - два типа, для каждого из которых есть implicit - оператор в другой тип?


#1502

Ну… вот, к примеру, сюрпризик.

begin
  var (a, b) := (1, 2);
  var c := a > b ? 1234567 : 1234567891011121314;
  Println(c)
end.

Я всегда говорил, что много разных целочисленных при отсутствии у процессора аппаратного контроля за переполнением - зло.


#1503

Ну правильно, тип всего - это тип integer. Тут оба типа могут преобразовываться один в другой.


#1504

Сделали. Это работает. Если один тип можно преобразовать к другому не пользовательскими преобразованиями, а второй нет, то общим выбирается второй тип. Если оба можно преобразовать один к другому, то выбирается левый

На всякий случай - вот страница MSDN: https://msdn.microsoft.com/ru-ru/library/ty67wk28(v=vs.120) Там ничего не сказано, что делать, если оба типа целочисленные


#1505

А разве не integer и int64 ? Другое дело, что int64 преобразуется к integer молча и простым копированием четырех байт из восьми. Такое ощущение, что тут С/С++ порылся.

А нельзя ли, чтобы выбирался не левый, а более “длиннобайтовый” для случая целых чисел ? Чтобы работало как в Справке для арифметических выражений? Для удобства и единообразия.


#1506

Ух ты, табличка какая классная! Где Вы её взяли?


#1507

Это шутка юмора была? Ваша же Справка…


#1508

@Admin Кстати, в этой табличке не хватает типа decimal.


#1509

Еще ошибки вывода типов (при участии Decimal):

begin
  // 1) Ошибка интеллисенса: 
  // Если один из операндов арифметической операции типа Decimal,
  // а второй -- типа ShortInt, Byte, SmallInt, Word или Integer, 
  // то результирующий тип отображается как Integer, а не Decimal.
  var r1 := decimal(1) + shortint(2);
  
  // 2) Ошибка интеллисенса: 
  // Если операнды Decimal и Int64, то результат по интеллисенсу всегда Int64, а не Decimal.
  var r2 := decimal(1) + int64(2);
  
  // 3) Ошибка компилятора:
  // Если один из операндов арифметической операции типа Decimal,
  // а второй -- типа LongWord или UInt64, то возникает ложная ошибка 
  // "Возможны два преобразования типов" при компиляции.
  var r3 := decimal(1) + uint64(2);
  
  // При этом также есть ошибка типа c интеллисенсом, но только для случая с Longword:
  // отображается тип Int64 вместо Decimal.
  var r4 := decimal(1) + longword(2);
end.

@Admin Фиксировать это в Issues?


#1510

Вы слишком увлеклись: в PascalABC.NET типа decimal нет. См. Справку. Это тип .NET, с которым Вы работаете на свой страх и риск.


#1511

Этим типом вообще мало кто пользуется. Во всяком случае я года за 3 ни разу и не вспоминал о нём.


#1512

Ну это Вы зря. Для финансовых расчетов с большими числами - самое то. 29 знаков с фиксированной точкой.


#1513

Я же не сказал, что никто не пользуется. :wink: Иначе его бы в .NET не было. Другое дело, что финансовыми расчётами занимается далеко не каждый программист. Говорят, что Decimal работает слишком медленно для научных вычислений, да и Single с Double спокойно удовлетворяют потребностям.


#1514

А Вы как считаете, если взять весь мир, в какой сфере больше программистов - в научной или в финансово-экономической?