ключевое слово var в C # 3.0

Возможный дубликат:
В чем смысл var ключевое слово?

Всем привет,

Я хочу подтвердить, правильно ли я понимаю. Если я не использую LINQ, то единственное преимущество использования var - это сокращение? Это правильное понимание?


person George2    schedule 18.07.2009    source источник
comment
Для ответа на этот вопрос нам нужен Джон Скит! :) В любом случае, см. Этот пост: stackoverflow.com/questions/209199/   -  person CalebHC    schedule 18.07.2009
comment
@George - просто ради интереса, вы пробовали искать на этом сайте многие предыдущие одинаковые вопросы? Иногда я задаюсь вопросом, полностью ли сломан поиск или что-то в этом роде.   -  person Daniel Earwicker    schedule 18.07.2009


Ответы (9)


Нет, вы можете использовать var для создания анонимных типов независимо от того, или нет, вы используете LINQ:

var anon = new { Name = "Anonymous", Age = 42 };
person LukeH    schedule 18.07.2009
comment
Можете ли вы написать этому анонимному типу, так что anon.Name = New Name; или это исправлено? - person Callum Rogers; 18.07.2009
comment
@C Роджерс. Да, это настоящий типаж. - person kenny; 18.07.2009
comment
@C Rogers - Что ж, свойства анонимных типов доступны только для чтения. - person JulianR; 18.07.2009

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

Dictionary<string, Dictionary<int, ICollection<object>>>

особенно если вы вернетесь и измените его на

Dictionary<string, IDictionary<int, ICollection<object>>>
person Sam Harwell    schedule 18.07.2009
comment
Вы можете исправить это с помощью using MyType = Dictionary<string, Dictionary<int, ICollection<object>>>; - person Daniel Earwicker; 18.07.2009
comment
Но не тогда, когда это тип, возвращаемый видимым методом. Вам нужно будет обеспечить единообразие операторов using во всех файлах, которые его используют. - person Sam Harwell; 18.07.2009

Из msdn:

Начиная с Visual C # 3.0, переменные, объявленные в области метода, могут иметь неявный тип var. Неявно типизированная локальная переменная строго типизирована, как если бы вы сами объявили тип, но компилятор определяет тип. Следующие два объявления i функционально эквивалентны:

var i = 10; // implicitly typed
int i = 10; //explicitly typed

Ссылка на MSDN здесь

person Sev    schedule 18.07.2009

Если вы не используете LINQ, var позволяет вам объявлять тип переменной только один раз, а не дважды.

Пример

var myObject = new MyObject();

vs

MyObject myObject = new MyObject();

Это можно сделать только локально, а также полезно для объявления анонимных типов.

Пример

var myAnon = new { Name = "Something", Count = 45 };
person Joseph    schedule 18.07.2009

За исключением запросов LINQ, я был бы очень осторожен при использовании ключевого слова var. Есть конкретный случай, когда вам просто нужен анонимный тип, но я думаю, что это немного и далеко друг от друга. Var может привести к очень запутанному коду, поскольку вы не знаете, с каким типом имеете дело при чтении кода, если не используете костыль intellisense.

Меня все больше и больше беспокоит то, что я вижу так много фрагментов и фрагментов кода, которые делают следующее ... это лениво, а не то, для чего было предназначено ключевое слово var:

// Not too bad but still shouldn't be done because the only gain you have is keystrokes
var Something = new SomeObject();

// Type here is not obvious, are you getting an int, double, custom object back???
var Something = GetLengthOfSpaghettiCode();

Так что используйте его для LINQ ... используйте его для анонимных типов (если вы действительно используете анонимные типы вне LINQ, вам действительно следует тщательно изучить, зачем вам это нужно).

Цитата из MSDN (самая последняя строка статьи) относительно использования var :

Однако использование var может, по крайней мере, сделать ваш код более трудным для понимания другими разработчиками. По этой причине в документации C # обычно используется var только тогда, когда это необходимо.

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

person Kelsey    schedule 18.07.2009
comment
Автозавершение кода и IDE достаточно, чтобы помочь разработчикам взглянуть на ваш код позже (не костыль, не ленивый - просто профессионал). Более того, правильные имена переменных раскрывают цель вашего кода. Ключевое слово var полезно, особенно в первом примере, приведенном в этом ответе, так как вы будете заниматься Хорошей вещью: DRY (Don't Repeat Yourself). Второй пример даже лучше, поскольку абстракция удалена. Что касается предполагаемого использования var, я хотел бы увидеть цитату. - person mkelley33; 18.07.2009
comment
Второй пример как раз и объясняет, почему это плохо. Предположим, что функция вернула int, а затем код функции был изменен, чтобы вернуть значение типа double. Ваше приложение все еще может нормально компилироваться, но дает совершенно непредусмотренные результаты. - person Kelsey; 18.07.2009
comment
Я думаю, что именно поэтому модульное тестирование и валидация являются хорошей практикой. Если намерение достаточно важно, поскольку оно относится к рассматриваемому типу, то оно должно пройти модульное тестирование и валидацию. - person mkelley33; 18.07.2009
comment
Или, что чаще всего, вполне приемлемые результаты. Обычно назначение метода и значение его возвращаемого типа очевидно из его имени. - person Jacob; 18.07.2009
comment
Скажи Джейкобу. Что касается цитаты о том, когда использовать var, обратите внимание, что она не объясняет назначение ключевого слова var и его использование. - person mkelley33; 18.07.2009
comment
Келси, я просто хочу поблагодарить вас за этот комментарий. На мой взгляд, разработчики, использующие var, крайне ленивы. Ничто не раздражает меня больше при отладке кода, чем вопрос о типе переменной. Почему мне нужно читать всю строку кода, чтобы увидеть, что это за переменная на самом деле? Потому что какой-то болван не удосужился объявить его тип? Еще раз спасибо, рад видеть здесь кого-то здравого смысла. - person Kevin; 18.07.2009
comment
Заблуждение состоит в том, что вам нужно знать тип каждой переменной. Было бы легче прочитать мое последнее предложение, если бы я поставил грамматический тип каждого слова в скобки перед ним? Или вы прекрасно это поняли по контексту и определениям? Тип - это деталь реализации, и теперь мы можем рассматривать ее как таковую. Сохранение нажатий клавиш только запутывает проблему и, очевидно, не является целью ключевого слова. - person Bryan Watts; 18.07.2009
comment
Брайан: Я не оспариваю цель ключевого слова var. Я думаю, что он отлично подходит для анонимных типов, и я думаю, что именно поэтому он был введен. Я утверждаю, что var something = CreateSomething (); это побочный эффект функции. Побочный эффект, позволяющий избежать нажатия клавиш за счет меньшей явности. - person Kelsey; 19.07.2009
comment
@Kelsey У тебя уже есть что-то дважды в этом заявлении. Я не вижу смысла добавлять его еще раз, чтобы сообщить компилятору то, что он уже знает. Любой человек знает, что это такое: вы назвали это как-то, а не как-то целиком. Кроме того, я еще не упомянул о том, что объявления переменных становятся стандартизированными. Глаз учится их читать (как в случае с циклами for), и вам не нужно читать имя типа целиком, чтобы узнать тип оператора. У вас уже есть метка для семантического значения переменной: ее имя. Вам действительно нужно всегда знать типаж? - person Bryan Watts; 19.07.2009
comment
Мой пример var something = CreateSometing (); не означало, что я создавал именно это, это должно было быть чем угодно. Как и мой оригинальный var Something = GetLengthOfSpaghettiCode (); Я не знаю, что такое var, пока не пойду посмотреть, как он используется. То же, что и var = 1; это int, unsigned int, nullable int или даже double. В любом случае оператор работает и компилируется, поэтому все сводится к стилю кодирования и предпочтениям. Мне это не нравится. Это не значит, что я прав или нет, это мое предпочтение. Это не тот форум, на котором можно обсуждать подобного рода;) - person Kelsey; 19.07.2009
comment
Выведено с ошибкой (ожидание, пока кто-нибудь перепрыгнет через это) var = 1; должно быть var something = 1; - person Kelsey; 19.07.2009

В значительной степени да. var может использоваться везде, где компилятор может вывести тип переменной из любого значения, которое вы ей присваиваете. (Однако правила вывода типов довольно сложны, поэтому вы можете прочитать спецификацию C # для полного понимания.)

Это не совсем правильно, поскольку ключевое слово var требуется для определения анонимных типов. Например:

var foo = new { abc = 1, def = 2 };

который, конечно, можно использовать как вне запросов LINQ, так и внутри.

person Noldorin    schedule 18.07.2009

Я не думаю, что использование var должно быть проблемой - и я предпочитаю его именно по причинам удобочитаемости кода. Прежде всего, var - это всего лишь синтаксический сахар и просто компилируется в правильный тип при испускании IL. Что касается читабельности кода, имеет смысл сосредоточиться не только на ее типе, но и на цели, для которой используется переменная и как она присваивается. Редактор VS .NET все равно показывает тип в следующей за ним строке - если вы просто наведете на него курсор. Так что это не должно быть проблемой. Что касается отладки - если вы видите окна Autos / Local / Watch - они отображают типы всех участников.

Для меня имеет смысл видеть такой код:

var customers = GetCustomerList();
foreach (var customer in customers)
{
  customer.ProcessOrders();
}

в отличие от

List<CustomerObjectDeserializedFromWebService> customers = GetCustomers();
foreach (CustomerObjectDeserializedFromWebService customer in customers)
{
  customer.ProcessOrders();
}

По своей справедливости var ограничивается использованием в объявлениях локальных переменных, которые также инициализируются во время объявления. И в этом одном случае, если вы опустите фактический тип, это определенно улучшит читаемость IMO.

РЕДАКТИРОВАТЬ: И было бы несправедливо с моей стороны не предупреждать об использовании, как показано ниже:

var x = 20;

Это не хорошо; когда литерал применим к нескольким типам, вам необходимо знать тип литерала по умолчанию и, следовательно, понимать, что передается для типа x. Да, я бы во что бы то ни стало избегал таких заявлений.

person Charles Prakash Dasari    schedule 18.07.2009

Я считаю, что он также используется в WCF (Windows Communication Foundation) при работе с данными, полученными через веб-службы и т.п.

person Garry    schedule 18.07.2009

Я также обнаружил, что использование var также упрощает рефакторинг в слабосвязанных проектах. Это потому, что мы склонны к сильным типам переменных, но обычно следующий код ожидает более слабых типов. Используя var, вы компенсируете изменения типа в компиляторе.

person Hugo Sereno Ferreira    schedule 18.07.2009