Лучшая практика с возможностью нулевого интерфейсного объекта в классе - PullRequest
0 голосов
/ 11 марта 2019

Я создал класс, который представляет компонент.Этот компонент имеет ширину, высоту, x-координату, y-координату и т. Д. Когда я манипулирую шириной, высотой, x и y, я хочу сохранить логику в классе.Но в классе компонентов есть объект интерфейса, который имеет аналогичные значения.Этот интерфейс может использоваться для общения с различными типами программного обеспечения САПР.Интерфейс Shape может быть нулевым.

Так что мой вопрос, что будет лучшим подходом для этого?В приведенном ниже примере, когда я изменяю «Y», я должен проверить на нулевое значение в интерфейсе формы?Или, возможно, класс компонентов имеет обработчики событий, и интерфейс Shape должен зарегистрироваться для них.Итак, что было бы наилучшей практикой для разработки этого подхода и что дало бы лучшую производительность?

Оцените это!

public class Component
{
    private double _y;

    public IShape Shape { get; set; }
    public string Name { get; set; }
    public double Width { get; set; }
    public double Height { get; set; }
    public double X { get; set; }

    public double Y
    {
        get => _y;

        set
        {
            _y = value;
            if (Shape != null) Shape.Y = value;
        }
    }

    public void Update_Shape()
    {
        //used to update the Shape Interface after it is assigned
    }

}

public interface IShape
{
    string Name { get; set; }
    double Width { get; set; }
    double Height { get; set; }
    double X { get; set; }
    double Y { get; set; }
}

ОБНОВЛЕНИЕ: Чтобы дать больше деталей, мой интерфейс сможет говоритьв Microsoft Visio и AutoCad.Они предназначены только для визуального представления данных, не контролируют количество фигур или их расположение.Таким образом, в моем приложении пользователь может перемещать или изменять ширину / высоту в приложении.Если у них есть Visio, открытый в то время, я хочу, чтобы он также обновлял формы Visio.Если он не открыт, то это не имеет значения (позже он будет обновлен).То же самое касается AutoCad.

1 Ответ

1 голос
/ 11 марта 2019

Лучшая практика в этой ситуации зависит от ваших целей проектирования.

Если вы хотите автоматически обновить IShape и производительность критична, то ручное выписывание ваших сеттеров с нулевой проверкой даст вам обоим. Наличие события, на которое подписывается IShape, заставляет вас вызывать событие, которое стоит дороже, чем проверка на ноль. И это имеет преимущество в сохранении беспорядка внутри класса, так как вам нужно только назначить myComponent.X = 20;

Наличие события имеет свои преимущества. Если вы посмотрите шаблон наблюдателя, вы сможете найти много хороших материалов по этому вопросу. Если у вас есть более одного IShape, который подписался бы на ваш Component, скажем, как из Visio, так и из AutoCad одновременно, это будет путь.

Теперь с точки зрения производительности, если вы обновляете менее нескольких тысяч компонентов в секунду и вам нужен более чистый код, я бы просто вызвал Update_Shape(), когда вы хотите синхронизировать значения. Если вы назначаете несколько значений одновременно, вы можете заключить их в действие, которое автоматически синхронизирует значения после его завершения.

var c = new Component();
c.Shape = new Shape();

c.UpdateShapes(s => {
    s.Height = 100;
    s.Width = 100;
    s.X = 5;
});
public class Component
{
    public IShape Shape { get; set; }
    public string Name { get; set; }
    public double Width { get; set; }
    public double Height { get; set; }
    public double X { get; set; }
    public double Y { get; set; }

    public void UpdateShapes(Action<Component> update)
    {
        update(this);
        SyncronizeShapes();
    }

    public void SyncronizeShapes()
    {
        if (Shape != null)
        {
            Shape.Name = Name;
            Shape.Width = Width;
            Shape.Height = Height;
            Shape.X = X;
            Shape.Y = Y;
        }
    }
}
...