C# класс с обязательными полями

У меня есть класс, все поля, в которых должны быть при создании объекта. Мое решение:

class MyClass
{
    private string Field1;
    private int Field2;

    public MyClass(string Field1, int Field2)
    {
        this.Field1 = Field1;
        this.Field2 = Field2;
    }
}

Но поля могут быть больше 2, код выглядит грязным. Есть ли более элегантный метод?

6 ответов

Решение

Передача полей, которые требуются конструкторам, должна быть в порядке. Ваш код еще не выглядит грязным, но если он начал расти, скажем, 10 обязательных полей, то лучше создать объект, который содержит все обязательные поля, а затем использовать этот объект при создании объекта (конструктор).

Прямо сейчас это не грязно

class MyClass
{
    private string Field1;
    private int Field2;

    public MyClass(string Field1, int Field2)
    {
        this.Field1 = Field1;
        this.Field2 = Field2;
    }
}

Если бы стало так

class MyClass
{
    private string Field1;
    private int Field2;

    public MyClass(string Field1, int Field2, int Field3, int Field4, int Field5, int Field6, int Field7, int Field8, int Field9, int Field10)
    {
        this.Field1 = Field1;
        this.Field2 = Field2;
        //Set them
    }
}

Тогда лучше иметь это

    class RequiredFields
{
    //All required fields
}

class MyClass
{
    private string Field1;
    private int Field2;

    public MyClass(RequiredFields requiredFields)
    {
        this.Field1 = requiredFields.Field1;
        this.Field2 = requiredFields.Field2;
        //Set them
    }
}

Можно использовать System.ComponentModel.DataAnnotations.RequiredAttribute.

[Required]
public string Field1{ get; set; }

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

С помощью длинных списков параметров конструктора именованные аргументы могут сделать вызов более читабельным.

Вы можете просто получить что-то подобное и затем ссылаться на объект всякий раз, когда вы пытаетесь получить доступ к полям в нем.

class MyClass
{
    private MyObject Test;

    public MyClass(MyObject Test)
    {
        this.Test = Test;
    }


}
class MyObject
{
    private string Field1;
    private int Field2;

    // Constructor / methods to set up fields
}

Я думаю, что вам нужен приватный конструктор, метод фабрики и именованные параметры, например:

class MyClass
{
    private string Field1;
    private int Field2;

    private MyClass()
    {

    }
    public MyClass GetMyClassInstance(string Field1=string.Empty, int Field2=-1)
    {
        this.Field1 = Field1;
        this.Field2 = Field2;
    }
}

Теперь вы можете добавить любое количество параметров для создания объекта MyClass.

Нет другого способа убедиться, что пользователь предоставляет значение для каждого поля, но вы можете указать значение по умолчанию самостоятельно.

Например, вы можете предоставить альтернативный конструктор, который создает объект с определенными значениями поля по умолчанию, например так:

public MyClass() : this(string.Empty, -1)
{
}

public MyClass(string Field1, int Field2)
{
    this.Field1 = Field1;
    this.Field2 = Field2;
}

Или в качестве альтернативы:

public MyClass(string Field1 = "", int Field2 = -1)
{
    this.Field1 = Field1;
    this.Field2 = Field2;
}
Другие вопросы по тегам