Привет и добро пожаловать в StackOverflow. Я позволил себе немного отредактировать ваш вопрос, чтобы увеличить ваши шансы на получение полезных ответов, надеюсь, вы не против.
Лассе В. Карлсен
Следует отметить , что, предполагая listэто IEnumerable<T>, они могут (и должны) только что использовалиsum = list.Count();
BlueRaja - Дэнни Pflughoeft
Я предполагаю, что это можно использовать для предотвращения «засорения» области видимости новым именем переменной, которое может быть использовано где-то еще, что может вызвать конфликт.
Тим Шмелтер
Ответы:
84
Это соглашение используется, когда вам не нужен параметр.
Это чаще встречается в Haskell и других функциональных языках. Я думаю, что это откуда.
Гейб Мутхарт
10
В Haskell, ML, Scala и других _это подстановочный знак при сопоставлении с образцом. Это в основном означает: «Мне все равно, я всегда хочу, чтобы это совпадало». Это «мне все равно» затем переносится, когда дело доходит до наименования вещей, которые вам не нужны, и оттуда оно перетекает на другие языки программирования. Он, например, также используется в Ruby для обозначения того же значения, что и в этом примере, хотя _в Ruby не имеет абсолютно никакого особого значения.
Это имя параметра, хотя и бесполезное, но оно обычно используется (по некоторым соглашениям), когда вам нужно указать, что выражение имеет параметр, чтобы код компилировался, но вам все равно об этом, так что вы просто проигнорируете это.
Он в основном использует синтаксис того, что представляет собой законный идентификатор в C #, и поскольку идентификатор может начинаться с подчеркивания и не содержать ничего другого, это просто имя параметра.
Да, я использовал его, когда создавал поток с использованием лямбда-выражения. Thread t= new Thread(()=>doSomething(x,y)); t.start();
amesh 03
Я предполагаю, что использование _ передает каждую переменную коллекции в лямбда-выражение, даже если оно не используется. Но когда мы используем (), этого может и не произойти. Я имею в виду параметр меньше лямбды.
amesh 03
Вам нужно попробовать это с помощью вызова метода ForEach. В конструкторе Thread есть перегрузка, которая принимает делегат, не принимающий никаких параметров. Попробуйте вызвать такой метод, как этот ForEach, который вместо этого принимает делегат, который принимает параметр.
Лассе В. Карлсен
29
_- допустимое имя переменной. Они просто используются _как переменные.
Поскольку выражение lamda в основном используется в коротком анонимном коде, поэтому имя переменной иногда не требуется, даже если они не используют переменную в блоке кода, поэтому они просто дают _ для краткого соглашения
Я также поддерживаю использование _ => _.method()однострочных лямбда-выражений с вызовом метода, поскольку это снижает когнитивный вес инструкции. Особенно при использовании обобщений письмо x => x.method()просто добавляет долю секунды к вопросу «Что это за« x »? Это координата в пространстве?».
Рассмотрим следующий случай:
Initialize<Client> ( _=>_.Init() );
Используемый с вызовом Generics, подчеркивание в этом случае работает как «символ обхода». Он избегает избыточности, определяя, что тип аргумента очевиден и может быть получен из использования - точно так же, как когда вы используете 'var' для предотвращения повторения объявления типа. Написание client=>client.Init()здесь просто сделало бы инструкцию длиннее, не добавляя к ней никакого смысла.
Очевидно, это не относится к параметрам, передаваемым в метод, который следует назвать описательно. Например.:Do( id=>Log(id) );
Использование одного параметра подчеркивания для вызовов методов вряд ли оправдано при использовании блока кода вместо однострочного, поскольку лямбда-идентификатор отключается от определения своего универсального типа. Обычно, когда один и тот же идентификатор должен использоваться повторно, дайте ему описательное имя.
Суть в том, что многословие оправдано только для устранения неоднозначности, особенно для лямбда-выражений, которые были созданы, в первую очередь, для упрощения создания анонимных делегатов. В любом случае следует руководствоваться здравым смыслом, сбалансировав разборчивость и лаконичность. Если символ является лишь «приманкой» к реальной функциональности, односимвольные идентификаторы вполне подойдут. Так обстоит дело с циклами For и буквами «i» и «j» в качестве индексаторов.
+1 за такой подход! Я был единственным, кто использовал символы подчеркивания в лямбдах, чтобы «снизить когнитивный вес», а не для того, чтобы показать, что этот параметр не используется. С подчеркиванием легче читать, особенно если много цепочек и вы можете сразу определить тип, как это часто бывает с запросами LINQ!
list
этоIEnumerable<T>
, они могут (и должны) только что использовалиsum = list.Count();
Ответы:
Это соглашение используется, когда вам не нужен параметр.
источник
_
это подстановочный знак при сопоставлении с образцом. Это в основном означает: «Мне все равно, я всегда хочу, чтобы это совпадало». Это «мне все равно» затем переносится, когда дело доходит до наименования вещей, которые вам не нужны, и оттуда оно перетекает на другие языки программирования. Он, например, также используется в Ruby для обозначения того же значения, что и в этом примере, хотя_
в Ruby не имеет абсолютно никакого особого значения.Это имя параметра, хотя и бесполезное, но оно обычно используется (по некоторым соглашениям), когда вам нужно указать, что выражение имеет параметр, чтобы код компилировался, но вам все равно об этом, так что вы просто проигнорируете это.
Он в основном использует синтаксис того, что представляет собой законный идентификатор в C #, и поскольку идентификатор может начинаться с подчеркивания и не содержать ничего другого, это просто имя параметра.
Вы могли бы легко написать:
источник
Thread t= new Thread(()=>doSomething(x,y)); t.start();
_
- допустимое имя переменной. Они просто используются_
как переменные.источник
Поскольку выражение lamda в основном используется в коротком анонимном коде, поэтому имя переменной иногда не требуется, даже если они не используют переменную в блоке кода, поэтому они просто дают _ для краткого соглашения
источник
Я также поддерживаю использование
_ => _.method()
однострочных лямбда-выражений с вызовом метода, поскольку это снижает когнитивный вес инструкции. Особенно при использовании обобщений письмоx => x.method()
просто добавляет долю секунды к вопросу «Что это за« x »? Это координата в пространстве?».Рассмотрим следующий случай:
Initialize<Client> ( _=>_.Init() );
Используемый с вызовом Generics, подчеркивание в этом случае работает как «символ обхода». Он избегает избыточности, определяя, что тип аргумента очевиден и может быть получен из использования - точно так же, как когда вы используете 'var' для предотвращения повторения объявления типа. Написание
client=>client.Init()
здесь просто сделало бы инструкцию длиннее, не добавляя к ней никакого смысла.Очевидно, это не относится к параметрам, передаваемым в метод, который следует назвать описательно. Например.:
Do( id=>Log(id) );
Использование одного параметра подчеркивания для вызовов методов вряд ли оправдано при использовании блока кода вместо однострочного, поскольку лямбда-идентификатор отключается от определения своего универсального типа. Обычно, когда один и тот же идентификатор должен использоваться повторно, дайте ему описательное имя.
Суть в том, что многословие оправдано только для устранения неоднозначности, особенно для лямбда-выражений, которые были созданы, в первую очередь, для упрощения создания анонимных делегатов. В любом случае следует руководствоваться здравым смыслом, сбалансировав разборчивость и лаконичность. Если символ является лишь «приманкой» к реальной функциональности, односимвольные идентификаторы вполне подойдут. Так обстоит дело с циклами For и буквами «i» и «j» в качестве индексаторов.
источник
Do(id => Log(id))
лучше сокращать какDo(Log)
.