您好我正在尝试创建抽象类Person和两个子类Student和Staff。 Person类还有一个由Practical类通知的观察者。但学生只会收到有关问题编号变更的通知,以及有关学生感觉良好因素的工作人员。任何学生都可以随时标记该因素。我设法让观察者工作,但只有Person类。我知道我要把它抽象化,然后创建职员和学生课程,但我无法理解它。任何帮助都会很棒。谢谢 这是代码:
namespace ConsoleApplication1
{
class Practical : IPractical //Practical class
{
private String QuestionNumber;// the state which observers are interested in.
private String Factor;
private ArrayList observers; // the collection of observers attached to this subject.
public Practical(String qnumber, String f)
{
QuestionNumber = qnumber;
Factor = f;
observers = new ArrayList();
}
public void AddObserver(IPerson o) { observers.Add(o); }
public void RemoveObserver(IPerson o) { observers.Remove(o); }
public void NotifyObserverQN()
{
foreach (IPerson o in observers) { o.Update(QuestionNumber); }
}
public void NotifyObserverFactor()
{
foreach (IPerson o in observers) { o.Update(Factor); }
}
public String QN
{
get { return QuestionNumber; }
set
{
QuestionNumber = value;
NotifyObserverQN(); //notify about new question
}
}
public String Fc
{
get { return Factor; }
set
{
Factor = value;
NotifyObserverFactor(); //notify about new ffctor
}
}
}
interface IPractical //IPractical interface
{
void AddObserver(IPerson o);
void RemoveObserver(IPerson o);
void NotifyObserverQN();
void NotifyObserverFactor();
}
class Person : IPerson
{
private string id;
public Person(string i) { id = i; }
public void Update(Object o) { Console.WriteLine(" {0} notified about {1} .", id, o.ToString()); }
}
interface IPerson //Observer interface
{
void Update(Object o);
}
class Observer
{
public static void Main()
{
Console.WriteLine("\n\nStart\n\n");
Practical practical = new Practical("Question", "Factor");
IPerson a, b, c;
a = new Person(" Student_1 ");
b = new Person(" Student_2 ");
c = new Person(" Staff_1 ");
practical.AddObserver(a);
practical.AddObserver(b);
practical.AddObserver(c);
practical.QN = "Question 1"; // all students notifie about Question 1
practical.Fc = "Feel-Good";
practical.QN = "Question 2"; // all students notifie about Question 2
practical.Fc = "Feel-Bad";
Console.WriteLine("\n\nEnd\n\n");
}
}
}
答案 0 :(得分:0)
理想情况下,您需要一个显式强制转换,以检查特定观察者是否为Student或Staff类型。在这种情况下,您可以将通知方法概括如下,而不是编写两种通知方法。
public void Notify()
{
foreach (IPerson o in observers)
{
if (IPerson is Student)
o.Update(QuestionNumber);// Student - question number
else
o.Update(Factor);//Staff - feel-good factor
}
}
根据关于继承如何在这种情况下工作的请求;
public abstract class Person : IPerson
{
private string id;
public Person(){}
public Person(string i)
{
id = i;
}
public abstract void Update(Object o);
}
public class Student:Person
{
public Student(){}
public Student(string i):base(i)
{
}
public override void Update(object o)
{
//whatever you wanted to do with Student
}
}
public class Staff : Person
{
public Staff(){}
public Staff(string i)
: base(i)
{
}
public override void Update(object o)
{
//whatever you wanted to do with Staff
}
}
interface IPerson //Observer interface
{
void Update(Object o);
}
答案 1 :(得分:0)
我想补充一点,在C#中,我更喜欢通过事件实现观察者。你不必让观察者知道谁在观察它们及其类型,而是在观察到的类中引发事件。在您的情况下,您将在Practical类中引发QuestionChanged和FactorChanged事件。当您创建观察者时,将其注册到您的员工和学生班级,他们将选择他们感兴趣的事件。这样,没有人知道另一个是什么类型。
像这样(伪代码,可能无法编译):
public class Practical {
...
public event EventHandler QNChanged;
public event EventHandler FcChanged;
public String QN
{
get { return QuestionNumber; }
set
{
QuestionNumber = value;
OnQNChanged(); //notify about new question
}
}
public String Fc
{
get { return Factor; }
set
{
Factor = value;
OnFcChanged(); //notify about new ffctor
}
}
protected void OnFcChanged(){
if(this.FcChanged != null) {
FcChanged(this, null);
}
}
protected void OnQnChanged(){
if(this.QnChanged != null) {
QnChanged(this, null);
}
}
...
}
public class Student {
public Student(Practical practical){
practical.QnChanged += Update;
}
public void Update(object sender, EventArgs args){
Practical practical = (Practical) sender;
// do something with practical
}
}
public class Staff{
public Staff(Practical practical){
practical.FnChanged += Update;
}
public void Update(object sender, EventArgs args){
Practical practical = (Practical) sender;
// do something with practical
}
}
class Observer
{
public static void Main()
{
....
var practical = new Practical("Question", "Factor");
var a = new Student(practical);
var b = new Staff(practical);
practical.QN = "Question 1"; // all students notified about Question 1
practical.Fc = "Feel-Good";
practical.QN = "Question 2"; // all students notified about Question 2
practical.Fc = "Feel-Bad";
....
}
}
注意:您不必在构造函数中包含观察到的项,也可以添加一个方法来注册它,如果您愿意,它只是使示例更简单。即,您的员工和学生可以实现此界面:
public interface IPracticalObserver {
void RegisterPractical(IPractical practical);
void Update(object practical, EventArgs args);
}