1:编写一个长方形类,
私有成员 a,b
构造函数初始化
set get 接口编写一个正方形类,继承自长方形类
构造函数初始化
无论如何,正方形类对象总是正方形的
#include <iostream>
#include <cstring>
#include <cstdlib>
#include <unistd.h>
#include <sstream>
#include <vector>
#include <memory>
using namespace std;
class Rectangle{
private:
int a;//长
int b;//宽
public:
Rectangle(int a=0,int b=0):a(a),b(b){}
void setA(int l){a = l;}
void setB(int l){b = l;}
int getA(){return a;}
int getB(){return b;}
};
class Square:public Rectangle{
public:
Square(int k=0):Rectangle(k,k){}
void setA(int a){
Rectangle::setA(a);
Rectangle::setB(a);
}
void setB(int a){
Rectangle::setA(a);
Rectangle::setB(a);
}
};
int main(int argc,const char** argv){
Square g;//正方形对象
g.setA(5);
cout << g.getA() << " " << g.getB() << endl;
g.setB(6);
cout << g.getA() << " " << g.getB() << endl;
}
写一个三角形类,拥有私有成员
a,b,c 三条边
2. 写好构造函数初始化 abc 以及 abc 的set get 接口再写一个等腰三角形类,继承自三角形类
1:写好构造函数,初始化三条边
2:要求无论如何,等腰三角形类对象,总是等腰的
再写一个等边三角形类,继承自等腰三角形类
1:写好构造函数,初始化三条边
2:要求无论如何,等腰三角形类对象,总是等边
#include <iostream>
#include <cstring>
#include <cstdlib>
#include <unistd.h>
#include <sstream>
#include <vector>
#include <memory>
using namespace std;
class ABC{
private:
int a;
int b;
int c;
public:
ABC(int a=0,int b=0,int c=0):a(a),b(b),c(c){}
void setA(int l){a = l;}
void setB(int l){b = l;}
void setC(int l){c = l;}
int getA(){return a;}
int getB(){return b;}
int getC(){return c;}
};
class AAC:public ABC{
public:
AAC(int ab=0,int c=0):ABC(ab,ab,c){}
void setA(int a){
ABC::setA(a);
ABC::setB(a);
}
void setB(int a){
ABC::setA(a);
ABC::setB(a);
}
};
class AAA:public AAC{
public:
AAA(int abc=0):AAC(abc,abc){}
void setA(int a){
AAC::setA(a);
ABC::setC(a);
}
void setB(int a){
AAC::setA(a);
ABC::setC(a);
}
void setC(int a){
AAC::setA(a);
ABC::setC(a);
}
};
int main(int argc,const char** argv){
AAC aac;
aac.setA(4);
cout << aac.getA() << " " << aac.getB() << " " << aac.getC() << endl;
aac.setB(5);
cout << aac.getA() << " " << aac.getB() << " " << aac.getC() << endl;
aac.setC(6);
cout << aac.getA() << " " << aac.getB() << " " << aac.getC() << endl;
AAA aaa;
aaa.setA(3);
cout << aaa.getA() << " " << aaa.getB() << " " << aaa.getC() <<endl;
aaa.setB(4);
cout << aaa.getA() << " " << aaa.getB() << " " << aaa.getC() <<endl;
aaa.setC(5);
cout << aaa.getA() << " " << aaa.getB() << " " << aaa.getC() <<endl;
}
3.封装消息队列
class Msg{
key_t key
int id;
int channel
}
实现以下功能
Msg m("文件名")
m[1].send("数据"),将数据发送到1号频道中
string str = m[1].recv(int size) 从1号频道中读取消息,并且返回把 send 改成 operator<< ,recv 改成 operator>>
实现效果:
m[1] << "helloworld" 将 "helloworld" 写入消息队列的1号频道中
m[1] >> str 读取消息队列中1频道中的消息,存入 str 中编写程序测试
#include <iostream>
#include <sys/ipc.h>
#include <sys/msg.h>
#include <cstring>
using namespace std;
class Msg {
private:
key_t key;
int id;
struct Msgbuf {
long channel;
char buf[128];
};
public:
// 子类:Channel
class Channel {
private:
int id;
long channel;
public:
Channel(int msg_id, long ch) : id(msg_id), channel(ch) {}
// 重载 operator<< 发送数据
void operator<<(const string &data) {
Msgbuf msg;
msg.channel = channel;
strncpy(msg.buf, data.c_str(), 127);
msg.buf[127] = '\0';
if (msgsnd(id, &msg, strlen(msg.buf) + 1, 0) == -1) {
perror("msgsnd");
}
}
// 重载 operator>> 接收数据
void operator>>(string &data) {
Msgbuf msg;
memset(&msg, 0, sizeof(msg));
if (msgrcv(id, &msg, sizeof(msg.buf), channel, IPC_NOWAIT) == -1) {
perror("msgrcv");
data = "";
return;
}
data = string(msg.buf);
}
};
// 构造函数
Msg() {
key = ftok("./ipc", 2);
if (key == -1) {
perror("ftok failed");
exit(1);
}
id = msgget(key, IPC_CREAT | 0666);
if (id == -1) {
perror("msgget failed");
exit(1);
}
}
// 重载 operator[] 返回 Channel 对象
Channel operator[](int ch) {
return Channel(id, ch);
}
};
int main() {
Msg m; // 创建消息队列对象
// 发送消息到 1 号频道
m[1] << "helloworld";
// 从 1 号频道读取消息
string str;
m[1] >> str;
cout << "Received: " << str << endl;
return 0;
}
4.封装信号灯集
class Sem{
key_t key
int id;
int index
}
实现以下功能
Sem s(参数x,参数y):创建信号灯集,信号灯集中存在 x 个信号量,并且将所有信号量初始化为 y
s[1].init(10):手动初始化信号灯集中的第1个信号量,初始化成 10
s[1] + 1 让信号灯集中的第1个信号量的值 +1
s[1].operator+(1)
s[1] - 1 让信号灯集中的第1个信号量的值 -1追加 operator ++ 功能,即解锁一次
以及 operator-- 功能, 即上锁一次编写程序测试
封装信号灯集
class Sem{
key_t key
int id;
int index
}
实现以下功能
Sem s(参数x,参数y):创建信号灯集,信号灯集中存在 x 个信号量,并且将所有信号量初始化为 y
s[1].init(10):手动初始化信号灯集中的第1个信号量,初始化成 10
s[1] + 1 让信号灯集中的第1个信号量的值 +1
s[1].operator+(1)
s[1] - 1 让信号灯集中的第1个信号量的值 -1
追加 operator ++ 功能,即解锁一次
以及 operator-- 功能, 即上锁一次
编写程序测试
#include <iostream>
#include <cstring>
#include <cstdlib>
#include <unistd.h>
#include <sstream>
#include <vector>
#include <memory>
#include <sys/sem.h>
using namespace std;
class Sem{
private:
key_t key;
int id;
int index;
public:
Sem(const string& filename = "", int n, int val) {
key = ftok(filename.data(), 1);
id = semget(key, n, IPC_CREAT | 0666);
for (int i = 0; i < n; i++) {
semctl(id, i, SETVAL, val);
}
}
~Sem() {
semctl(id, 0, IPC_RMID);
}
friend Sem& operator+(const Sem& l, int val);
friend Sem& operator-(const Sem& l, int val);
friend Sem operator[](const Sem& l, int index);
// operator++ 解锁一次
friend Sem& operator++(Sem& l, int) {
sembuf buf = {0};
buf.sem_num = l.index;
buf.sem_op = 1; // 解锁一次
buf.sem_flg = SEM_UNDO;
semop(l.id, &buf, 1);
return l;
}
// operator-- 上锁一次
friend Sem& operator--(Sem& l, int) {
sembuf buf = {0};
buf.sem_num = l.index;
buf.sem_op = -1; // 上锁一次
buf.sem_flg = SEM_UNDO;
semop(l.id, &buf, 1);
return l;
}
};
// Sem s
// s + 1解锁
// s - 1 上锁
// s + 1 + 1 + 1 - 2 - 3
// int(4) + 3
Sem& operator+(const Sem& l, int val) {
sembuf buf = {0};
buf.sem_num = l.index;
buf.sem_op = abs(val);
buf.sem_flg = SEM_UNDO;
semop(l.id, &buf, 1);
return const_cast<Sem&>(l);
}
Sem& operator-(const Sem& l, int val) {
sembuf buf = {0};
buf.sem_num = l.index;
buf.sem_op = -abs(val);
buf.sem_flg = SEM_UNDO;
semop(l.id, &buf, 1);
return const_cast<Sem&>(l);
}
Sem operator[](const Sem& l, int index) {
Sem temp = l; // 创建一个副本,因为我们不能修改const对象
temp.index = index;
return temp;
}
int main() {
Sem s("semfile", 1, 1); // 创建一个信号量,初值为1
// 测试解锁和加锁
s[0] + 1; // 解锁一次
s[0] - 1; // 上锁一次
s[0]++; // 解锁一次
s[0]--; // 上锁一次
return 0;
}