Почему конструкция with() не включена в C#, хотя в VB.NET она очень хороша?

StackOverflow https://stackoverflow.com/questions/429890

  •  07-07-2019
  •  | 
  •  

Вопрос

Я разработчик C#.Мне очень нравятся фигурные скобки, потому что я работал на C, C++ и Java.Однако мне также нравятся другие языки программирования семейства .NET, такие как VB.NET.Переключение между C# и VB.NET не так уж и сложно, если вы какое-то время программировали на .NET.Это очень распространенный подход в компании, где я работаю.Мне, как специалисту по C#, очень нравится XML-литерал и with ключевые слова, предоставляемые компилятором VB.NET.Мне бы хотелось, чтобы Microsoft включила эти функции и в C#.

Мне просто любопытно, что об этом скажет другой разработчик!

Это было полезно?

Решение

Я не удивлюсь, если в конечном итоге в C# будет добавлена ​​функция With или подобная функция вместе с другими ранее популярными исключительно функциями VB.Недавно в превью-презентациях C# 4.0 на PDC и других местах было много разговоров о возросшем «внимании к языковому равенству», начиная с C# 4.0 и VB 10.

Другие советы

Лично мне не нравится, когда OF используется после создания — если вам нужно сделать несколько вещей с объектом после его инициализации, обычно это поведение должно быть инкапсулировано в самом типе.Если вы действительно хотите сделать что-то вроде С, достаточно объявить короткую переменную и, при необходимости, ввести новую область видимости.

Однако это является полезно иметь возможность компактно инициализировать объект с несколькими свойствами — именно поэтому C# 3 позволяет писать:

MyObject x = new MyObject { Name="Fred", Age=20, Salary=15000 };

У этого есть ограничения (которые помогут преодолеть необязательные и именованные параметры в C# 4), но это лучше, чем было, и не приводит к потенциальным беспорядкам/двусмысленностям.

(Что касается XML-литералов, я снова с командой C#: XML — это очень специфическая технология для внедрения в язык.Если бы они могли придумать обобщенный form, которая предназначена для создания XML, но может использоваться и для создания других деревьев, это было бы неплохо - так же, как выражения запроса не связаны напрямую с IEnumerable или IQueryable.)

Вы можете заменить на в VB.Net, создав быстрое однобуквенное имя переменной. На самом деле это меньше кода, поскольку With также требует End With позже.

Например, одна вещь, которую мне приходилось делать довольно часто, это итерация по строкам в таблице данных для отчета в стиле control / break.

На vb.net это может выглядеть так:

Dim CurCustomerName As String 
Dim CustomerSalesTotal As Decimal

Dim ds As DataSet = GetReportData()
With ds.Tables(0).Rows
   Dim i As Integer = 0
   While i < .Count
       ''//{
       CurCustomerName = .Item(i)("CustName")
       CustomerSalesTotal = 0
       PrintHeaderLine(CurCustomerName)

       While i < .Count AndAlso CurCustomerName = .Item(i)("CustName")
            ''//{
            PrintItemLine(.Item(i)("OrderTotal"))
            CustomerSalesTotal += .Item(i)("OrderTotal")

            i+= 1
       End While ''//}
       PrintSubTotalLine(CustomerSalesTotal)
   End While ''//}
End With

C # будет выглядеть так:

string CurCustomerName;
Decimal CustomerSalesTotal;

DataSet ds = GetReportData();
DataRowCollection r = ds.Tables[0].Rows;
int i=0;
while (i<r.Count)
{
    CurCustomerName = r[i]["CustName"];
    CustomerSalesTotal = 0;
    PrintHeaderLine(CurCustomerName);

    while (i<r.Count && CurCustomerName == r[i]["CustName"])
    {
        PrintItemLine(r[i]["OrderTotal"]);
        CustomerSalesTotal += r[i]["OrderTotal"];

        i++;
    }
    PrintSubTotalLine(CustomerSalesTotal);
}

Здесь следует отметить, что версия C # на самом деле нуждалась в меньшем наборе текста, потому что VB не мог объединить WITH с индексом массива и должен был пройти через .Item свойство для определенных вещей. Здесь нет ничего сложного, но представьте, что в отчете было 20 полей вместо 2 и нужно было разбить 3 элемента вместо 1.

Конечно, вы можете использовать технику, продемонстрированную в C #, и для VB. Но главное, на что нужно обратить внимание, это то, что WITH действительно мало что дает.

Это касается предпочтений разработчика, но я с вами о WITH. Я предпочитаю минимизировать количество переменных в игре и область, в которой они живут. Философия C # кажется почти такой же. Но в этом случае ответы здесь, по-видимому, предполагают, что добавление (и принятие на себя ответственности) переменной - это хорошо, по сравнению с конструкцией, которая, на мой взгляд, очень похожа на лямбду.

Я чувствую, что довольно произвольно разрешать установку «массовых» свойств во время инициализации. Я действительно не понимаю, почему это будет «плохо»:

MyObj myObj = ObjFactoryFunction();

...

if(someCondition)
  myObj { Prop1 = 1, Prop2 = 2 };

Мне кажется, что этот пример кода чистый и лаконичный.

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

Мне нравится, как работает мой код, когда я встраиваю свободный интерфейс в объект; он имеет некоторые сходства с с . Если бы я проектировал MessageBox.Show () , я мог бы написать:

new MessageBox()
    .SetText("Hello World!")
    .SetButtons(MessageBox.Buttons.OK)
    .SetIcon(MessageBox.Icon.Information)
    .Show();

Вы также можете увидеть нечто похожее с Linq:

var q = Enumerable.Range(1, 100)
            .Where(x => x % 2 == 0)
            .Select(x => x * x);

Это похоже на с , но, кажется, естественно вписывается в язык, который я уже имею.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top