코딩 공부/디자인패턴

옵저버 패턴

공부를 함 2024. 12. 3. 15:02

Observer Pattern

#region Interfaces
public interface ISubject
{
    public void RegisterOb(IObserver o);
    public void RemoveOb(IObserver o);
    public void NotifyOb();
}
public interface IObserver
{
    public void Update(WeatherData wd);
}

public interface IDisplay
{
    public void Display();
}
#endregion

#region BaseClasses
public struct WeatherData
{
    private float temp;
    private float humidity;
    private float pressure;
    public WeatherData(float temp, float humidity, float pressure)
    {
        this.temp = temp;
        this.humidity = humidity;
        this.pressure = pressure;
    }
    public float GetTemp() { return temp; }
    public float GetHumidity() { return humidity; }
    public float GetPressure() { return pressure; }
}

public class DataController : ISubject
{
    private List<IObserver> observers;
    private WeatherData wd;
    
    public DataController()
    {
        observers = new List<IObserver>();
    }
    
    public void RegisterOb(IObserver o) { observers.Add(o); }
    public void RemoveOb(IObserver o) { observers.Remove(o); }
    public void NotifyOb() { foreach (var o in observers) o.Update(wd); }
    public void MeasurementsChanged() { NotifyOb(); }
    public void SetMeasurements(float temp, float humidity, float pressure) { wd = new WeatherData(temp, humidity, pressure); MeasurementsChanged(); }
    
}
#endregion

#region DisplayClasses
public class CurrentConditionDisplay : IObserver, IDisplay
{
    private float temperature;
    private float humidity;
    private DataController dc;
    
    public CurrentConditionDisplay(DataController dc)
    {
        this.dc = dc;
        dc.RegisterOb(this);
    }
    
    public void Update(WeatherData wd)
    {
        this.temperature = wd.GetTemp();
        this.humidity = wd.GetHumidity();
        Display();
    }

    public void Display() { Console.WriteLine($"Current conditions: {temperature}F degrees and {humidity}% humidity"); }
}
#endregion

public class WeatherStation
{
    public static void Main(String[] args)
    {
        DataController dc = new DataController();
        CurrentConditionDisplay ccd = new CurrentConditionDisplay(dc);
        
        dc.SetMeasurements(80, 65, 30.4f);
        dc.SetMeasurements(70, 55, 20.4f);
        dc.SetMeasurements(60, 45, 10.4f);
    }
}

 

 

옵저버가 데이터를 pull하는 형식으로 변경하려면, 수정사항은 아래와 같다.

public interface IObserver
{
    public void Update();
}
public void NotifyOb() { foreach (var o in observers) o.Update(); }
    public void Update()
    {
        this.temperature = dc.wd.GetTemp();
        this.humidity = dc.wd.GetHumidity();
        Display();
    }

 

'코딩 공부 > 디자인패턴' 카테고리의 다른 글

어댑터 패턴, 퍼사드 패턴  (1) 2024.12.04
커맨드 패턴  (0) 2024.12.04
팩토리 패턴  (0) 2024.12.03
데코레이터 패턴  (0) 2024.12.03
전략 패턴  (1) 2024.12.03