#ifndef REGISTRY_REGISTRY_H
#define REGISTRY_REGISTRY_H
#include
#include "patient.h"
#include "doctor.h"
#include "appointment.h"
class Registry {
public:
Registry();
~Registry();
std::vector> GetPatients() const;
std::vector> GetDoctors() const;
std::vector> GetAppointments() const;
void SetPatients(std::vector> patients);
void SetDoctors(std::vector> doctors);
void SetAppointments(std::vector> appointments);
void Add(Doctor doctor);
void Add(Patient patient);
void Add(DoctorID doctorId, PatientID patientId, Date date);
void Remove(PatientID id);
void Remove(DoctorID id);
void Remove(AppointmentID id);
std::vector> FindAppointments(DoctorID id);
std::vector> FindAppointments(PatientID id);
void ShowAll(const std::vector> &patients) const;
void ShowAll(const std::vector> &doctors) const;
void
ShowAll(const std::vector> &appointments,
const std::vector> &patients) const;
void
ShowAll(const std::vector> &appointments,
const std::vector> &doctors) const;
void ShowAll(const std::vector> &appointments,
const std::vector> &patients,
const std::vector> &doctors) const;
private:
std::vector> patients_;
std::vector> doctors_;
std::vector> appointments_;
void Remove(std::vector>::iterator itDoctor);
void Remove(std::vector>::iterator itPatient);
void Remove(std::vector>::iterator itAppointment);
std::vector>::iterator Find(PatientID id);
std::vector>::iterator Find(DoctorID id);
std::vector>::iterator Find(AppointmentID id);
};
#endif //REGISTRY_REGISTRY_H#include "../include/registry.h"
#include "../include/idgenerator.h"
#include
using namespace std;
Registry::Registry() {
}
Registry::~Registry() {
}
vector> Registry::GetPatients() const {
return patients_;
}
vector> Registry::GetDoctors() const {
return doctors_;
}
vector> Registry::GetAppointments() const {
return appointments_;
}
void Registry::SetPatients(vector> patients) {
patients_ = patients;
}
void Registry::SetDoctors(vector> doctors) {
doctors_ = doctors;
}
void Registry::SetAppointments(vector> appointments) {
appointments_ = appointments;
}
void Registry::Add(Doctor doctor) {
doctors_.emplace_back(IdGenerator::Generate(), doctor);
}
void Registry::Add(Patient patient) {
patients_.emplace_back(IdGenerator::Generate(), patient);
}
void Registry::Add(DoctorID doctorId, PatientID patientId, Date date) {
auto itDoctor = Find(doctorId);
if (itDoctor == doctors_.end()) {
throw invalid_argument("Лікаря з таким кодом не існує");
}
auto itPatient = Find(patientId);
if (itPatient == patients_.end()) {
throw invalid_argument("Пацієнта з таким кодом не існує");
}
Appointment newAppointment(itPatient->first, itDoctor->first, date);
// emplace_back - вместо того, чтобы принимать value_type, он принимает вариативный список аргументов, так что это означает,
// что теперь вы можете идеально пересылать аргументы и напрямую создавать объект в контейнере без временного хранения.
appointments_.emplace_back(IdGenerator::Generate(), newAppointment);
}
void Registry::Remove(PatientID id) {
auto it = Find(id);
if (it == patients_.end()) {
throw invalid_argument("Пацієнта з таким кодом не існує");
}
Remove(it);
}
void Registry::Remove(DoctorID id) {
auto it = Find(id);
if (it == doctors_.end()) {
throw invalid_argument("Лікаря з таким кодом не існує");
}
Remove(it);
}
void Registry::Remove(AppointmentID id) {
auto it = Find(id);
if (it == appointments_.end()) {
throw invalid_argument("Прийому пацієнта до лікаря з таким кодом не існує");
}
Remove(it);
}
vector> Registry::FindAppointments(DoctorID id) {
auto it = Find(id);
if (it == doctors_.end()) {
throw invalid_argument("Лікаря з таким кодом не існує");
}
vector> doctorAppointments;
string doctorKey = it->first;
copy_if(appointments_.begin(), appointments_.end(), back_inserter(doctorAppointments),
[&doctorKey](const pair &appointment) {
return appointment.second.GetDoctorKey() == doctorKey;
});
return doctorAppointments;
}
vector> Registry::FindAppointments(PatientID id) {
auto it = Find(id);
if (it == patients_.end()) {
throw invalid_argument("Пацієнта з таким кодом не існує");
}
vector> patientAppointments;
string patientKey = it->first;
copy_if(appointments_.begin(), appointments_.end(), back_inserter(patientAppointments),
[&patientKey](const pair &appointment) {
return appointment.second.GetPatientKey() == patientKey;
});
return patientAppointments;
}
void Registry::Remove(vector>::iterator itPatient) {
string patientKey = itPatient->first;
patients_.erase(itPatient);
// Удаляю все приемы в которых удаленный пациент
// erase - удаляет из вектора один элемент (позицию), либо диапазон элементов.
appointments_.erase(
// remove_if - элементы удовлетворяющие условию записывает в конец вектора, и возвращает итератор на начало элементов на удаление
remove_if(appointments_.begin(), appointments_.end(),
[&patientKey](const pair &appointment) {
return appointment.second.GetPatientKey() == patientKey;
}), appointments_.end());
}
void Registry::Remove(vector>::iterator itDoctor) {
string doctorKey = itDoctor->first;
doctors_.erase(itDoctor);
appointments_.erase(
remove_if(appointments_.begin(), appointments_.end(),
[&doctorKey](const pair &appointment) {
return appointment.second.GetDoctorKey() == doctorKey;
}), appointments_.end());
}
void Registry::Remove(vector>::iterator itAppointment) {
appointments_.erase(itAppointment);
}
vector>::iterator Registry::Find(PatientID id) {
// find_if - возвращает итератор к первому элементу в диапазоне [first, last], для которого предикат возвращает true.
// Если такой элемент не найден, функция возвращает last.
auto it = find_if(patients_.begin(), patients_.end(),
[&id](const pair &patient) {
return patient.second.GetID() == id;
});
return it;
}
vector>::iterator Registry::Find(DoctorID id) {
auto it = find_if(doctors_.begin(), doctors_.end(),
[&id](const pair &doctor) {
return doctor.second.GetID() == id;
});
return it;
}
vector>::iterator Registry::Find(AppointmentID id) {
auto it = find_if(appointments_.begin(), appointments_.end(),
[&id](const pair &appointment) {
return appointment.second.GetID() == id;
});
return it;
}
void Registry::ShowAll(const vector> &patients) const {
for (int i = 0; i < patients.size(); i++) {
patients[i].second.Show();
cout << endl;
}
}
void Registry::ShowAll(const vector> &doctors) const {
for (int i = 0; i < doctors.size(); i++) {
doctors[i].second.Show();
cout << endl;
}
}
void Registry::ShowAll(const vector> &appointments,
const vector> &patients) const {
for (int i = 0; i < appointments.size(); i++) {
cout << endl;
AppointmentID appointmentId = appointments[i].second.GetID();
cout << "Номер прийому: " << appointmentId << endl << endl;
string patientKey = appointments[i].second.GetPatientKey();
auto patientIt = find_if(patients.begin(), patients.end(), [&patientKey](const pair &patient) {
return patient.first == patientKey;
});
patientIt->second.Show();
cout << endl;
Date date = appointments[i].second.GetDate();
cout << "Дата прийому: ";
date.Show();
cout << endl;
}
}
void Registry::ShowAll(const vector> &appointments,
const vector> &doctors) const {
for (int i = 0; i < appointments.size(); i++) {
cout << endl;
AppointmentID appointmentId = appointments[i].second.GetID();
cout << "Номер прийому: " << appointmentId << endl << endl;
string doctorKey = appointments[i].second.GetDoctorKey();
auto doctorIt = find_if(doctors.begin(), doctors.end(), [&doctorKey](const pair &doctor) {
return doctor.first == doctorKey;
});
doctorIt->second.Show();
cout << endl;
Date date = appointments[i].second.GetDate();
cout << "Дата прийому: ";
date.Show();
cout << endl;
}
}
void Registry::ShowAll(const vector> &appointments,
const vector> &patients,
const vector> &doctors) const {
for (int i = 0; i < appointments.size(); i++) {
cout << endl;
AppointmentID appointmentId = appointments[i].second.GetID();
cout << "Номер прийому: " << appointmentId << endl << endl;
string patientKey = appointments[i].second.GetPatientKey();
auto patientIt = find_if(patients.begin(), patients.end(), [&patientKey](const pair &patient) {
return patient.first == patientKey;
});
patientIt->second.Show();
cout << endl;
string doctorKey = appointments[i].second.GetDoctorKey();
auto doctorIt = find_if(doctors.begin(), doctors.end(), [&doctorKey](const pair &doctor) {
return doctor.first == doctorKey;
});
doctorIt->second.Show();
Date date = appointments[i].second.GetDate();
cout << endl;
cout << "Дата прийому: ";
date.Show();
cout << endl;
}
}大家好,我想实现一个医院注册课程。但我不知道该怎么做。
它应包含病人、医生和病人对医生的预约。
它应该具有添加、删除病人、医生和医生预约等功能。为了正确删除对象,应该有搜索这些对象的方法。
我还想做一个功能,例如,搜索病人与某些医生的预约。
对象,例如病人有结构字段PatientID,这些ID是在对象创建时在构造函数中生成的,并且具有数字形式(0、1、2.)。例如,我将其作为一种结构来执行Remove()方法中的重载。
在类中,我计划将对象成对存储,这是对字符串的第一个元素(对象键,类似于UUID),是对的第二个元素--对象本身。这些键将在Add()方法中生成。我不能使用在对象构造函数中生成的ID对象,因为在每次重新启动程序之后,它们可以是不同的,并且不允许将病人和医生绑定在约会对象中,所以我计划将病人和医生的密钥保存在指定对象中,以便绑定它们,因为键只生成一次,而且不会更改。
我认为我的实现不是很好,因为现在它只关注对象if,但是如果我想按名称搜索对象呢?在这种情况下,我不知道如何生成重载的方法。你的建议是什么?正确的方法是什么?
发布于 2022-12-11 16:56:19
当标准库函数(包括模板函数)更好地匹配我们认为正在调用的函数时,using namespace std;可能会带来惊喜。名称空间的存在可以帮助我们分离类似命名的函数,并通过将整个std拖到全局命名空间中来丢弃它,这是非常有害的。
如果您真的觉得无法使用这五个字符std::,那么请考虑将特定的名称导入全局命名空间--即便如此,我还是建议您将它们的范围保持得很小(至少您没有在头中这样做,因为它会损害使用它的每个程序!)
还不清楚为什么我们有这么多的向量对-其中大多数看起来会更好作为std::map对象,特别是因为我们已经写了很多线性搜索它们。
我很惊讶你需要六种超负荷的Remove() --私有的每种都被调用一次,所以只需在它们的呼叫站点内嵌入它们。
通过维护每个医生和病人对其约会对象(可能是std::reference_wrapper对象的集合)的反向引用,您可以使FindAppointments()和D7简单得多(而且速度更快)。当然,您需要确保在更改(添加、修改或删除)约会时正确地更新这些内容。
在一对second元素上有很多匹配的搜索,使用std::find_if。我们可以编写一个方便的函数来生成所有类似的函子:
auto match_id(auto const& id)
{
return [&id](auto const& pair){ return pair.second.GetID == id; };
}这样我们就可以写
auto Registry::Find(const PatientID& id)
{
return std::ranges::find_if(patients_, match_id(id));
}和类似的。但是,考虑向find算法提供一个投影参数,并避免需要谓词函数,可能会更有成效。例如。
auto Registry::Find(const PatientID& id)
{
using PatientPair = std::pair;
return std::ranges::find(patients, id, &PatientPair::second);
}https://codereview.stackexchange.com/questions/281860
复制相似问题