Model view controller 在MVC中通知观察者的最佳方式?
假设某个视图感兴趣的模型中有5或6个变量,您是否为每个变量编写了不同的函数,例如Model view controller 在MVC中通知观察者的最佳方式?,model-view-controller,design-patterns,Model View Controller,Design Patterns,假设某个视图感兴趣的模型中有5或6个变量,您是否为每个变量编写了不同的函数,例如 int a; int b; int c; void setA( newA ) { a = newA; notifyAObservers(); } void setB( newB ) { b = newB; notifyBObservers(); } void setC( newC ) { b = newC; notifyCObservers(); } 还是只有一种通知方法
int a;
int b;
int c;
void setA( newA ) {
a = newA;
notifyAObservers();
}
void setB( newB ) {
b = newB;
notifyBObservers();
}
void setC( newC ) {
b = newC;
notifyCObservers();
}
还是只有一种通知方法,浪费了一点CPU时间
i、 e.与NotifyAObserver和NotifyBobserver不同,您只需要notifyObservers,我认为最重要的是通知所有观察者,并让他们处理。这是因为你不知道哪些观察者正在观察哪些变量——你只知道他们希望在某些事情发生变化时得到通知。然而,如果您确实知道观察者在观察哪些变量,并且性能非常关键,那么您可能可以做一些类似于您所做的事情
在传统的观察者模式中,观察者实现一个update()方法,当发生更改时,控制器会调用该方法。观察对象(数据模型)将有一个notifyObservators()方法,该方法迭代观察对象并调用其update()方法。然后,观察者得到他们需要的任何东西,视图更新
然而,每当我实现了观察家模式时,我都会简单地保留一个观察家列表并通知他们所有人。这样,我只有一个观察者列表,而班上的其他人以及不同的观察者都可以更改,而无需我对可观察的类通知进行任何更改。编辑:几年前我写了我的答案。刚刚读完之后,我觉得我需要更新一下 我认为最好的办法是通知所有观察者,让他们决定是否需要更新自己 每个视图将能够验证模型的状态并相应地采取行动。 此外,“args”可以用作一个标志来指示发生了什么变化(视图可能不希望每一个微小的变化都更新自己) 这样,模型实际上不知道视图显示的方式和内容,它们是解耦的 第一个实现如下所示:
public class MyModelV1 extends Observable {
private int value;
public void setValue(int value) {
this.value = value;
setChanged();
notifyObservers();
}
public int getValue() {
return value;
}
}
public class MyViewV1 implements Observer {
public void update(Observable o, Object arg) {
if (o instanceof MyModelV1) {
System.out.println(((MyModelV1) o).getValue());
}
}
}
视图只是检查接收到的可观察对象的类型。
但是,如果模型有许多属性,并且触发了许多不同场景的视图,那么这个简单的检查可能会过于频繁地刷新视图
另一种办法是:
public class MyModelV2 extends Observable {
private int value;
public void setValue(int value) {
this.value = value;
setChanged();
notifyObservers("value");
}
public int getValue() {
return value;
}
}
public class MyViewV2 implements Observer {
public void update(Observable o, Object arg) {
if (o instanceof MyModelV2 && "value".equals(arg)) {
System.out.println(((MyModelV2) o).getValue());
}
}
}
在这里,通知传递一个限定符,该限定符让视图更精确地决定何时刷新自身。
视图仍然需要检查并强制转换模型,因为无法保证arg“value”不会被另一个模型通知(并且强制转换将在运行时失败)
我个人最喜欢的是以下几点:
public class MyModelV3 extends Observable {
private int value;
public void setValue(int value) {
this.value = value;
setChanged();
Notification.MY_MODEL_VALUE_UPDATED.notifyObserver(this);
}
public int getValue() {
return value;
}
}
public class MyViewV3 implements Observer {
public void update(Observable o, Object arg) {
if (Notification.MY_MODEL_VALUE_UPDATED.equals(arg)) {
MyModelV3 model = Notification.MY_MODEL_VALUE_UPDATED.getModel(o);
System.out.println(model.getValue());
}
}
}
public class Notification<T extends Observable> {
public static final Notification<MyModelV3> MY_MODEL_VALUE_UPDATED = new Notification<MyModelV3>();
private Notification() {
}
public T getModel(Observable o) {
return (T) o;
}
public void notifyObserver(T observable){
observable.notifyObservers(this);
}
}
公共类MyModelV3扩展了可观察{
私有int值;
公共无效设置值(int值){
这个值=值;
setChanged();
通知.MY_MODEL_VALUE_UPDATED.notifyObserver(此);
}
public int getValue(){
返回值;
}
}
公共类MyViewV3实现了Observer{
公共无效更新(可观察o,对象arg){
if(通知.MY_MODEL_VALUE_UPDATED.equals(arg)){
MyModelV3 model=Notification.MY\u model\u VALUE\u UPDATED.getModel(o);
System.out.println(model.getValue());
}
}
}
公开课通知{
公共静态最终通知MY_MODEL_VALUE_UPDATED=新通知();
私人通知(){
}
公共T模型(可观测o){
返回(T)o;
}
公共观察者(T可观察){
可观察。通知观察者(本);
}
}
这里,通知发送一个绑定到模型的强类型限定符。
视图能够使用通知检索强类型模型(而不是强制转换)
这是介于观察者和事件总线之间的某个位置。它还使事情变得简单,因为有办法找出哪些观察者正在观察哪个变量。然而,这最终可能看起来很复杂。你能给我举个简单的例子吗,托马斯?我已经投票支持你,但是在视图中将实现哪些方法,如何通知他们,等等。谢谢!你的意思是说所有的观察者只需实现一个“notify()”方法,然后他们每次都会轮询模型中他们感兴趣的数据。例如,notifyObservators()直接遍历观察者列表并调用notify()。每个观察者从模型中提取所需的数据,并相应地更新其视图。就像变量A被更改一样,B-Observators仍然会得到一个notify()调用,并且会说类似于B=model.getB(),即使B没有更改?我不确定您在寻找什么-我文章中的链接有Java和Python中的Observator模式示例。你能详细说明你有什么具体问题吗?当我发表我的评论时,你发表了你的第二条评论。但是是的,你是对的。我也在我原来的帖子中添加了这个。