我已经按照自己的水平进行了尝试,但没有成功。还阅读了博客,但没有引导我找到正确的解决方案。
我的要求基于观察者设计模式,在此模式下,主题(或发布者)将在机器/服务器的CORE号.1上连续运行,并为“温度,湿度和压力”生成一些随机数。
现在,我想在另一个名为核心5的核心上启动一个进程(例如,观察者/订阅者),该核心将在任何给定的时间点尝试向主题或发布者注册以查看“温度”最近生成的数字,湿度和压力”,然后在发布后立即开始从“主题/发布者”获取更新。
我所做的是:
a)创建了一个类对象,该类对象具有registerObserver,deregisterObserver和notifyObservers作为方法,并且还具有noOfObservers作为属性,因此一旦发生注册,它就会增加一个..
b)创建具有方法更新(浮子温度,浮子湿度,浮子压力)的接口类观察者
c)创建一个从Subject派生的WeatherData类(具有注册,取消注册..方法)。该方法具有 changeState(浮动温度,浮动湿度,浮动压力)方法,该方法从主题类中调用notifyObservers(因为主题类应该具有所有已注册的观察者)。
d)应用程序weather.cpp会创建一个WeatherData类的对象,它会生成随机数并调用带有温度,湿度和压力的changeState()。这将在一个特定的核心号上运行。一台机器
e)在客户端/观察者/订户端:我创建了一个程序client.cpp,它创建了一个Client-Class实例,该实例是从Observer接口派生的,并将Subject Class的静态方法称为如下: Subject :: registerObserver(cltptr);
如果此注册完全发生在其他内核上,我已经做了一些cout语句来显示。要看到这一点,我每次调用registerObserver时都将计数器加1。
但是,似乎无法在不同的Core上单独运行WeatherStation(主题/发布者)和客户端(观察者/订阅者)的应用程序。
如果某个大师已经做到了这一点,并且可以帮助我更正此问题,以便Weatherstation和Client可以独立运行,那么我将非常感激他/她。
主要思想是在不同的内核上运行Observer和Subject,并且仍然能够相互通信。对我来说,推/拉/回调可以正常工作,但一点点优化。想法是使它分别在不同的内核上以某种方式工作。
在Internet中,大多数示例是针对一个内核,线程等上的所有内容的,目前我还不是这种情况。
感谢所有帮助。
示例代码如下所示:
**------------------------------weather.cpp----------------------------------**
// ------------------------ This is the WeatherStation / Subject / Publisher --!
#include <iostream>
#include "ifobserver.h"
#include "ifsubject.h"
#include "weather.h"
#include <unistd.h>
float randomnumber(float limit) {
/* return a random number between 0 and limit inclusive.
*/
float divisor = RAND_MAX/(limit+1);
float retval;
do {
retval = rand() / divisor;
} while (retval > limit);
return retval;
}
int main(int argc, char **argv) {
float temp = 16;
float humidity = 30.2;
float pressure = 2.9;
WeatherData weatherStation; // just like platform...
int lookups = 0;
while(true) // unlimited loop for weather changes...
{
temp = randomnumber(45.0);
humidity = randomnumber(80.0);
pressure = randomnumber(9);
weatherStation.changeState(temp, humidity, pressure); // this sill nofity all Observers...
++lookups;
usleep(200000); // 200 milliseconds..
if(lookups>= 50000)
{ std::cout << "All cycles ended" << std::endl;
return false;
}
}
return 0;
}
**------------------------------weather.h----------------------------------**
#ifndef WEATHER_H_
#define WEATHER_H_
#include "ifobserver.h"
#include "ifsubject.h"
#include <iostream>
// Specific implementation of Subject Interface...
class WeatherData : public Subject {
float temp = 0.0f;
float humidity = 0.0f;
float pressure = 0.0f;
public:
/**
* Set the new state of the weather station
* @param temp new temperature
* @param humidity new humidity
* @param pressure new pressure
*/
void changeState(float temp, float humidity, float pressure)
{
this->temp = temp;
this->humidity = humidity;
this->pressure = pressure;
std::cout << "New-Temp , Humidtiy, Pressure=" << this->temp << "," << this->humidity << "," << this->pressure
<< "....registerd Observers = " << noOfObservers << std::endl;
notifyObservers(temp, humidity, pressure);
}
};
#endif /* WEATHER_H_ */
**------------------------------ifobserver.h----------------------------------**
#ifndef IFOBSERVER_H_
#define IFOBSERVER_H_
/**
* Interface for the Observer
*/
class Observer {
public:
/**
* Update the state of this observer
* @param temp new temperaure
* @param humidity new humidity
* @param pressure new pressure
*/
virtual void update(float temp, float humidity, float pressure) = 0;
virtual ~Observer() {}
};
#endif /* IFOBSERVER_H_ */
**------------------------------ifsubject.h----------------------------------**
#ifndef IFSUBJECT_H_
#define IFSUBJECT_H_
#include "ifobserver.h"
#include <algorithm>
#include <vector>
#include <iostream>
class Subject {
protected :
inline static int noOfObservers;
public:
Subject() {
std::cout << "Constructor()" << std::endl;
}
static void registerObserver(const Observer *observer) {
++noOfObservers;
std::cout << "registerObserver() - called: Address=" << observer << ", No-of-subcribers" << noOfObservers << std::endl;
}
static inline void deregisterObserver(const Observer *observer) {
// // to remove first, we have to find them and then remove
//// auto itr = std::find(observers.begin( ), observers.end( ), observer);
////
//// if (itr != observers.end())
//// observers.erase(itr);
std::cout << "deregisterObserver() - called: Address=" << observer << std::endl;
}
static void notifyObservers(float& temp, float& humidity, float& pressure) {
if (noOfObservers <= 0)
return;
std::cout << "notifyObservers() - called =" << temp << "," << humidity << "," << pressure << std::endl;
}
};
**------------------------------client.h----------------------------------**
#ifndef CLIENT_H_
#define CLIENT_H_
#include "ifobserver.h"
#include <iostream>
class Client : public Observer {
int id;
public:
Client(int& id) : id(id) { std::cout << "Client-No:" << id << "created" << std::endl;}
void update(float temp, float humidity, float pressure)
{
std::cout << "Temp , Humidtiy, Pressure=" << temp << "," << humidity << "," << pressure << std::endl;
}
};
#endif /* CLIENT_H_ */
// ------**********************************************************--------------//
**------------------------------client.cpp----------------------------------**
// This is the Client, which tries to register itself to the Publisher to get weather updates on separate Cores..
#include <iostream>
#include "client.h"
#include "ifsubject.h"
#include <unistd.h>
int main(int argc, char **argv) {
int i = 0;
Client * clptr[20];
while (i < 20)
{
clptr[i] = new Client(i);
Subject::registerObserver(clptr[i]);
usleep(500000);
++i;
}
// delete memory
for( int i = 0; i < 20; ++i)
{
delete clptr[i];
}
return 0;
}