themePath не используется, поскольку https://github.com/ajaxorg/ace-builds/blob/master/webpack-resolver.js явно устанавливает пути для всех тем. Если вы хотите использовать themePath, не загружайте webpack-resolver
count
- это int, а int - это типы значений, что означает, что они действительно передаются по значению. Между вашим первым и вторым примером нет семантической разницы.
(Тем не менее, мне кажется, что он должен увеличивать count
, поскольку он должен захватывать исходную ссылку до закрытия. Чтобы уточнить - хотя счетчик будет передаваться по значению вниз в SomeFunction, вещи не передаются в ваше лямбда-выражение, когда вы используете их внутри выражения - они являются той же ссылкой, что и внешняя переменная.)
В обоих случаях вы создаете так называемое закрытие. По сути, count помещается в класс, и этот класс используется лямбда-выражением.
У Билла Вагнера есть отличная книга под названием More Effective C # , и у него есть сообщение в блоге, описывающее крышки более подробно.
Нет, разницы нет. Аргументы обычно имеют значение, если вы явно не указали его «ref» или «out» в определении делегата, используемом для лямбда.
Это должно зафиксировать (закрыть) счет как закрытие .
Лямбда-выражения являются анонимными функциями и, как таковые, следуют тем же правилам, что и передача аргументов в функцию.
Счетчик переменной перехватывается лямбда-выражением в вашей ситуации. Любые изменения в счетчике
будут видны вызывающему абоненту. Так, например:
int count = 0;
list.ForEach(i => i.SomeFunction(count++));
Console.WriteLine(count);
отобразит размер списка, потому что на каждой итерации вы увеличиваете счетчик
.
Однако вызов SomeFunction
передает вычисленное значение count ++
(которое является значением count
до приращения) на значение от до SomeFunction
. Другими словами, SomeFunction
не может изменить значение count
.
Подробнее о замыканиях и захвате переменных см. В моей статье о замыканиях .
]Это должно увеличиваться, доказательство:
class Foo
{
public void SomeFunction(int i) { }
}
static void Main()
{
int count = 0;
List<Foo> list = new List<Foo> {new Foo()};
list.ForEach(i => i.SomeFunction(count++));
Console.WriteLine(count); // 1
}
Лямбда действует (как уже говорилось) для «захвата» счетчика, по сути делая код примерно таким:
class Foo
{
public void SomeFunction(int i) { }
}
class CaptureScope
{
public int count;
public void AnonMethod(Foo foo)
{
foo.SomeFunction(count++);
}
}
static void Main()
{
CaptureScope scope = new CaptureScope();
scope.count = 0;
List<Foo> list = new List<Foo> {new Foo()};
list.ForEach(scope.AnonMethod);
Console.WriteLine(scope.count); // 1
}
Вышеупомянутое является грубым приближением того, как компилятор интерпретирует лямбда-выражение делегата. Как видите, счетчик
является полем в классе, а увеличивается на .
Я хотел добавить здесь небольшую поправку. Счетчик переменных не передается ни по значению, ни по ссылке на лямбда-выражение, потому что это не параметр. Вместо этого значение фиксируется лямбдой в замыкании.
Вам стоит посмотреть серию работ Раймонда на эту тему. - http://blogs.msdn.com/oldnewthing/archive/2006/08/02/686456.aspx
В этом случае count
переменная захвачена . Даже если это структура
, захваченная переменная действует как ссылка . Таким образом, вы наверняка увидите увеличенный счетчик
после foreach
.