В C# это тоже не работает:
int? j = true ? null : 5;
В C# это тоже не работает:
int? j = true ? null : 5;
Там сообщение об ошибке другое
Тут разрешает НЕ ставить точки с запятой:
type
t1=class
b1:byte
public
b2:byte
end;
begin end.
А с методами так не проходит:
type
t1=class
function f1:byte := 0
public
function f2:byte := 0
end;
begin end.
Так и задумано?
К сожалению, да. В конце секции можно не ставить. Это сделано для совместимости с Delphi и Borland Pascal. Там такое компилируется
type
t1=record
b1:byte
end;
Методов внутри там нет, потому для методов мы это уже запретили
15 мая был откачен фикс #796, и с того момента стало ещё хуже. Теперь не только компилятор не работает для var d: t1 := (a + b).f1
. Теперь эта строчка ещё и полностью ломает анализатор кода:
Точки сворачивания просто не появляются.
Можете, пожалуйста, объяснить ситуацию с этой issue, чтоб я понимал что является ошибкой а что нет?
И, желательно, исправить хотя бы сообщение об ошибке, потому что Встречено '.', а ожидалось ';'
полностью сбивает с толку. В такой короткой строчке ещё можно догадаться что не так, но я успел отбить себе лоб об эту невидимую стену, в местах где всё не так элементарно.
Конструкция (a + b).f1 давала конфликты в грамматике. Как-то мы это пропустили.
Конфликты в грамматике - это вот что такое. Это значит, что правильная программа случайно может оказаться неправильной и наоборот. Причем, непредсказуемо. Это - кошмар.
Эта ошибка просуществовала какое-то время. Плохо, что мы её заметили не сразу. Откатили.
По поводу сообщения об ошибке. Оно Вам не нравится, но оно верное. После (a+b) может идти точка с запятой. Точка теперь идти не может. Вот и выдаётся это сообщение об ошибке.
t1(a + b) - это вызов функции - после него точка может идти
То, что Вы хотите всё-таки точку, вас сбивает
Вот так работает - уже прекрасно )))
begin
var (a, b) := (3, 5);
(a+b).ToString.Println
end.
Ну так правильно. В заголовке issue
так и сказано, надо не только оператор, а ещё и объявление переменной с : <тип этой переменной>
. И это главная проблема. Во всех случаях после скобок даёт ставить точку. По крайней мере я не знаю таких. А тут, вдруг.
Но это всё же не повод говорить что вы никогда не исправите. Хотя бы оставьте ту issue
, отложив в долгий ящик. Это всё же лучше.
И что с анализатором кода? Он, вроде, на момент создания issue не был сломал и сломался только после отката. То как он себя в этой ситуации ведёт - ну очень не хорошо.
Ну, мы не умеем побеждать конфликты в грамматике и заставлять солнце двигаться в другую сторону. Можно конечно Issue на что угодно, но не поможет.
Хорошо, если вы не будете исправлять - напишите об этой особенности языка в справке или где то ещё. И добавьте своё сообщение об ошибке, которое будет объяснять почему это всюду после скобочек можно использовать точку, а тут нельзя. Такого типа:
Использование "." после оператора, на строчке с объявлением переменной и её типа - запрещено
.
Длинно, но вы поймите, отсутствие нормального объяснения не только сбивает с толку в смысле “а что я сделал не так?”, а ещё и в смысле “это ошибка или так и задумано?”. Через пол года, когда я забуду про эту недо-фичу - я снова потрачу много времени на попытки найти что вызвало такое странное поведение, только чтоб в конце понять что это ещё один дубль #796. Очень демотивирует, знаете ли, когда много труда и времени выбрасывается в форточку.
begin
var d:=new Dictionary<byte,word>;
d.Add(1,2);
//var s:sequence of word := d.Values + word(5);//Ошибка: Нет перегруженной подпрограммы с такими типами параметров
var s:sequence of word := IEnumerable&<word>(d.Values) + word(5);
s.Println;//Выводит "2 5", как и ожидалось
end.
Почему тут не даёт написать d.Values + word(5)
, это ошибка?
Есть серия issue. Общее у них то что у как то полученной записи вызывается метод, и компилятор создаёт для этого вызова не правильный IL код. Прослеживается следующая тенденция:
Я вот не могу вспомнить, есть ещё какой то способ получить запись? Напишите, если знаете, если с этим способом тоже генерируется не правильный IL код - возможно получится исправить ошибку до того как она сломает чью то программу.
@admin, @ibond, можете пожалуйста посмотреть сюда и сказать, является ли внутренняя ошибка при компиляции test.pas
ещё 1 проявлением #951?
Там 5 модулей, циклично скреплённых друг с другом, очень не хочется без лишней причины всё это разгребать))).
свойство типа записи, поле типа запись, приведение оbject к типу запись
Инициализация массива массивов в сокращенной форме. Ошибка выполнения: Индекс находился вне границ массива.
begin
var c: array of array of integer := ((1,2,3),(4,5,6,7),(6,7,8)); //тут ошибка рантайма
c.Println
end.
А вот пример, который в справке
begin
var c: array of array of integer := ((1,2,3),(4,5),(6,7,8));
c.Println;//[1,2,3] [4,5,0] [6,7,8]
end.
вроде бы и работает, но почему второму под-массиву (ну который первый по индексу) дописывается третий элемент - 0?
Да, это правильно. Память подстраивается под первую строку.
Вообще, эту инициализацию я бы запретил - именно из-за неё у нас большие проблемы с различием между
var x := выражение;
и
То есть, синтаксис старой Delphi нас тянет назад
var x: T := выражение;
Так это ошибка или нет, я не понял. А еще можно спросить, у вас написано в справке, что
var a := Arr(Arr(1,3,5),Arr(7,8),Arr(5,6)); // array of array of integer
но при наведении на переменную в рамке пишет: var a: array of T;
как это понять, компилятор не выводит тип или справка не соответствует?
Это не ошибка.
Система Intellisense, выводящая типы при наведении, у нас не такая мощная и не выводит тип T.
Ну, в #884 вы тоже сказали что это слишком сложно для вашего анализатор кода, но оказалось просто. Давайте всё же разберёмся перед тем как говорить что вы не сможете это реализовать.