Эти строки полностью аналогичны
O>C1 x = new C1(); O>var x2 = new C1();
И эти строки, соответственно, тоже полностью аналогичны
O>Console.WriteLine(x.Run()); // C1 is running O>Console.WriteLine(x2.Run()); // ну и какой же Run() вызывать? C1.Run, конечно, как и в предыдущей строке.
O>Console.WriteLine(((I1)x).Run()); // I1 is running O>Console.WriteLine(((I2)x).Run()); // I2 is running
O>В общем-то, не вижу смысла в var.
Я вижу, что ты не видишь смысла Смысл такой, что реальные классы имеют имена куда длиннее, чем `C1`, и к тому же
int[] integers;
foreach (var el in integers) ;
foreach (int el in integers) ;
Ну и тому подобные применения. Всегда, когда тип вновью создаваемой переменной равен типу правой части (т.е. никаких касто вне происходит), можно этот тип не писать. Конечно, если это не приносит ущерба читаемости.
O>// работающий код O>Base x = new Derived(); O>Console.WriteLine(x.Hello()); // Hi from Base O>Console.WriteLine(((Derived)x).Hello()); // Hi from Derived
O>// гипотетический код O>var x2 = new Derived(); O>Console.WriteLine(x2.Hello()); // опять же, какой Hello вызывать
Вот так понятнее?
var Derived = new Derived();
Console.WriteLine(x2.Hello()); // опять же, какой Hello вызывать
Насколько я помню, в C# будет ошибка компиляции во второй строке, и правильно. Но `var` тут ни при чем.
O>IMHO: var в C# не место.
Ты всё еще не понял. Это не сущность, это макрос. typeof(new Derived()) всегда равно `Derived` и никогда не равно `Base`. Тип переменной x2 — `Derived`, независимо от того, сколько каких интерефейсов кто-то где-то реализовал. У typeof по определению только один результат — не может быть никакой неоднозначности.
[... skipped ...]
Кё>Ну и тому подобные применения. Всегда, когда тип вновью создаваемой переменной равен типу правой части (т.е. никаких касто вне происходит), можно этот тип не писать. Конечно, если это не приносит ущерба читаемости.
Экономя на символах, составляющих название класса, мы запутаем сами себя. Например, если в массиве сидят объекты типа Base (отсюда — Re[2]: Синтаксический оверхед в C# / Java
O>>// работающий код O>>Base x = new Derived(); O>>Console.WriteLine(x.Hello()); // Hi from Base O>>Console.WriteLine(((Derived)x).Hello()); // Hi from Derived
O>>// гипотетический код O>>var x2 = new Derived(); O>>Console.WriteLine(x2.Hello()); // опять же, какой Hello вызывать
Кё>Вот так понятнее? Кё>var Derived = new Derived();
Я уже понял, что ты имеешь в виду. Хотел тебе показать, что var принесёт кучу неоднозначности в код.
Кё>Console.WriteLine(x2.Hello()); // опять же, какой Hello вызывать
Кё>Насколько я помню, в C# будет ошибка компиляции во второй строке, и правильно. Но `var` тут ни при чем.
Ошибка компиляции? У меня, видно, компилятор поломался — всё компилится.
O>>IMHO: var в C# не место.
Кё>Ты всё еще не понял. Это не сущность, это макрос. typeof(new Derived()) всегда равно `Derived` и никогда не равно `Base`. Тип переменной x2 — `Derived`, независимо от того, сколько каких интерефейсов кто-то где-то реализовал. У typeof по определению только один результат — не может быть никакой неоднозначности.
Ну а толку-то от такого макроса? Я всё ещё не могу понять — неужели от экономии символов столько пользы, что её можно проделывать засчёт понижения читабельности кода?
O>Base[] array; O>foreach (var x in array) { O> Console.WriteLine(x.Hello()); O>} O>и если хоть один из них на самом деле имеет тип Derived, то поведение будет отличаться от поведения такого кода:
Тип элемента "на самом деле" никак не должен волновать инструкцию var. Если в массиве элементы Base, то var x аналогично Base x. Dervied тут никак не участвует.
O>Base[] array; O>foreach (Base x in array) { O> Console.WriteLine(x.Hello()); O>} O>- согласен?
Не согласен. Не будет отличаться. Ты вкладываешь в `var` какое-то слишком сложное поведение, тогда как его смысл — подсмотреть тип выражения и подставить вместо себя.
Может ты неправильно понимаешь typeof, о котором я говорю? Я не про шарповский, я про гипотетический С++-ный говорил.
class Base {}
class Derived : Base {}
Base ba = new Derived();
typeof(ba) всегда Base и никогда Derived.
[... skipped ...]
Кё>Может ты неправильно понимаешь typeof, о котором я говорю? Я не про шарповский, я про гипотетический С++-ный говорил. Кё>class Base {} Кё>class Derived : Base {}
Кё>Base ba = new Derived(); Кё>typeof(ba) всегда Base и никогда Derived.
Да, тут я тебя недопонял, согласен. Получается, var — действительно только макрос, который обрабатывается на этапе прекомпиляции. И всё-таки Баба Яга против добавления такого сахара. Мой глубочайшее имхо заключается в том, что макросы — зло. Даже в том случае, если они используются крайне редко (как ключевое слово var, например).
O>Ну а толку-то от такого макроса? Я всё ещё не могу понять — неужели от экономии символов столько пользы, что её можно проделывать засчёт понижения читабельности кода?
Я специально оговорил — только если это не понимает читаемость. var применяется, если переменная уничтожается через шесть строк. Определять переменную через var и затем использовать на следующей странице будет очень плохо, я согласен
В качестве компромисса можно сделать его фичей IntelliSense. Т.е. вы пишете var, вместо которого редактор подставляет имя типа.
O>>Ну а толку-то от такого макроса? Я всё ещё не могу понять — неужели от экономии символов столько пользы, что её можно проделывать засчёт понижения читабельности кода?
Кё>Я специально оговорил — только если это не понимает читаемость. var применяется, если переменная уничтожается через шесть строк. Определять переменную через var и затем использовать на следующей странице будет очень плохо, я согласен
В Си тоже макросы добавили во имя благих целей...
Кё>В качестве компромисса можно сделать его фичей IntelliSense. Т.е. вы пишете var, вместо которого редактор подставляет имя типа.
Oyster,
O>Да, тут я тебя недопонял, согласен. Получается, var — действительно только макрос, который обрабатывается на этапе прекомпиляции. И всё-таки Баба Яга против добавления такого сахара. Мой глубочайшее имхо заключается в том, что макросы — зло. Даже в том случае, если они используются крайне редко (как ключевое слово var, например).
Макрос макросу рознь. Если макрос устраняет дублирование, то макрос — хорошо, а дублирование — плохо.
O>Base[] array;
O>foreach (var x in array) {
O> Console.WriteLine(x.Hello());
O>}
O>
O>и если хоть один из них на самом деле имеет тип Derived, то поведение будет отличаться от поведения такого кода:
Нет. Вывод типа происходит статически те тип переменной x будет Base.
Тип можно легко вывести в большинстве мест. По крайней мере у ReSharper'а это очень хорошо получается.
O>В общем, имхо проблем больше, чем преимуществ.
Не согласен.
Здравствуйте, WolfHound, Вы писали:
WH>Здравствуйте, Oyster, Вы писали:
O>>
O>>Base[] array;
O>>foreach (var x in array) {
O>> Console.WriteLine(x.Hello());
O>>}
O>>
O>>и если хоть один из них на самом деле имеет тип Derived, то поведение будет отличаться от поведения такого кода: WH>Нет. Вывод типа происходит статически те тип переменной x будет Base. WH>Тип можно легко вывести в большинстве мест. По крайней мере у ReSharper'а это очень хорошо получается.
Ок, это я уже понял.
O>>В общем, имхо проблем больше, чем преимуществ. WH>Не согласен. WH>
Здравствуйте, Кодёнок, Вы писали:
Кё>В качестве компромисса можно сделать его фичей IntelliSense. Т.е. вы пишете var, вместо которого редактор подставляет имя типа.
Поставь ReSharper
... << RSDN@Home 1.1.4 beta 6a rev. 436>>
Пусть это будет просто:
просто, как только можно,
но не проще.
(C) А. Эйнштейн
Здравствуйте, Oyster, Вы писали:
Кё>>Я специально оговорил — только если это не понимает читаемость. var применяется, если переменная уничтожается через шесть строк. Определять переменную через var и затем использовать на следующей странице будет очень плохо, я согласен O>В Си тоже макросы добавили во имя благих целей...
Так давай отделим мух от катлет и часть языка от макросов. Макросы в С плохи не по тому что они скрывают что-то, а по тому что они не учитывают другие синтаксические конструкции языка и заменяют что попало например макросы min/max из windows.h очень портят нервы когда пытаешься использовать STL и WinAPI совмесно. (особенно пока не знаешь про NOMINMAX)
... << RSDN@Home 1.1.4 beta 6a rev. 436>>
Пусть это будет просто:
просто, как только можно,
но не проще.
(C) А. Эйнштейн
В умных средах это кстати уже есть, только с другой стороны: набираем имя класса, имя переменной, "= new ", Ctrl+Shift+Space и получаем все _совместимые_ типы.
Здравствуйте, WolfHound, Вы писали:
WH>Здравствуйте, Oyster, Вы писали:
Кё>>>Я специально оговорил — только если это не понимает читаемость. var применяется, если переменная уничтожается через шесть строк. Определять переменную через var и затем использовать на следующей странице будет очень плохо, я согласен O>>В Си тоже макросы добавили во имя благих целей... WH>Так давай отделим мух от катлет и часть языка от макросов. Макросы в С плохи не по тому что они скрывают что-то, а по тому что они не учитывают другие синтаксические конструкции языка и заменяют что попало например макросы min/max из windows.h очень портят нервы когда пытаешься использовать STL и WinAPI совмесно. (особенно пока не знаешь про NOMINMAX)
Мух от котлет? Запросто. Строк через 50 кода мы уже забудем, что у нас там в переменной auto x, поэтому можем свято верить, что вызываем один метод, хотя вызовем другой (спасибо программеру Джону, он переопределил значение, возвращаемое методом GetSth() и теперь auto x = GetSth() содержит значение не типа A, а типа B).
Здравствуйте, Кодёнок, Вы писали:
Кё>В качестве компромисса можно сделать его фичей IntelliSense. Т.е. вы пишете var, вместо которого редактор подставляет имя типа.
Лучше наоборот — по левой части предлагать соответствующие подсказки длоя правой. Кстати о new — современные редакторы после new предлагают список конструкторов в соответствии с типом левой части выражения, так что напрактике его (new) отмена приведет только к большей трудоемкости набора кода.
Кё>>В качестве компромисса можно сделать его фичей IntelliSense. Т.е. вы пишете var, вместо которого редактор подставляет имя типа.
AVK>Лучше наоборот — по левой части предлагать соответствующие подсказки длоя правой. Кстати о new — современные редакторы после new предлагают список конструкторов в соответствии с типом левой части выражения, так что напрактике его (new) отмена приведет только к большей трудоемкости набора кода.
Что-то я глубоко сомневаюсь, что IntelliSense когда-нибудь сможет предложить `Some.Namespace.daFunction(new System.Drawing.Point(30,5))` в качестве правой части
Здравствуйте, Oyster, Вы писали:
O>>IMHO: var в C# не место.
O>... и Да здравствует строгая типизация!
Советую обратить внимание на языки с системой типов Хиндлей-Миллнера (с выведением типов, естественно). Сдается мне, это то, что вы тут неявно обсуждаете.
Здравствуйте, WFrag, Вы писали:
O>>... и Да здравствует строгая типизация!
WF>Советую обратить внимание на языки с системой типов Хиндлей-Миллнера (с выведением типов, естественно). Сдается мне, это то, что вы тут неявно обсуждаете.
Не совсем (или совсем не). В C#-то уже другая система типов.