diff --git a/src/parser.cpp b/src/parser.cpp index e724163..3c6347e 100644 --- a/src/parser.cpp +++ b/src/parser.cpp @@ -415,7 +415,7 @@ namespace /* internal */ if(val == 0) err_unexpected_char('.'); else if(unknown) - return EventTime::UNKNOWN_DATE; + return UNKNOWN_DATE; else return sign * val; break; diff --git a/src/person.cpp b/src/person.cpp index f10618f..c79de2b 100644 --- a/src/person.cpp +++ b/src/person.cpp @@ -1,4 +1,5 @@ #include +#include #include #include #include @@ -7,17 +8,14 @@ #include "utils.hpp" #include "ui.hpp" -using std::cout; -using std::string; +using namespace std; -EventTime::EventTime(I16 Year, U8 Month, U16 Day, I8 Hour, I8 Minute) +EventTime::EventTime(I16 Year, U8 Month, U16 Day) : year(Year) , month(Month) , day(Day) - , hour(Hour) - , minute(Minute) { - assert(month <= 12 && day <= 31 && hour <= 23 && minute <= 59 && "Invalid EventTime data"); + assert(month <= 12 && day <= 31 && "Invalid EventTime data"); } void EventTime::print(WINDOW* info_tab) const @@ -42,21 +40,47 @@ void EventTime::print(WINDOW* info_tab) const } -Person::Person(const char* aName, EventTime aBirth, Sex aSex, EventTime aDeath) +Person::Person(const char* aName, Sex aSex, EventTime aBirth, EventTime aDeath) : name(aName) - , birth(aBirth) , sex(aSex) + , birth(aBirth) , death(aDeath) { } - -bool Person::operator==(const Person &other)const +static string_view nameWithoutFamily(const string& name) { - return sex == other.sex && name == other.name && - (birth.day == other.birth.day || birth.day == EventTime::UNKNOWN_DATE || other.birth.day == EventTime::UNKNOWN_DATE) && - (birth.month == other.birth.month || birth.month == EventTime::UNKNOWN_DATE || other.birth.month == EventTime::UNKNOWN_DATE) && - (birth.year == other.birth.year || birth.year == EventTime::UNKNOWN_DATE || other.birth.year == EventTime::UNKNOWN_DATE); + U32 fam_start = name.rfind(' ') ; + string_view name_no_fam; + + if(fam_start != string::npos) + name_no_fam = string_view(name.data(), name.size() - fam_start); + else + name_no_fam = string_view(name); + + return name_no_fam; +} + +bool Person::likelySame(const Person& other)const +{ + bool dates_pass = (birth.day == other.birth.day || birth.day == UNKNOWN_DATE || other.birth.day == UNKNOWN_DATE) && + (birth.month == other.birth.month || birth.month == UNKNOWN_DATE || other.birth.month == UNKNOWN_DATE) && + (birth.year == other.birth.year || birth.year == UNKNOWN_DATE || other.birth.year == UNKNOWN_DATE); + + bool names_pass; + if(sex == M) + { + names_pass = name == other.name; + } + else + { + string_view name_no_fam = nameWithoutFamily(name); + string_view other_name_no_fam = nameWithoutFamily(other.name); + + names_pass = name_no_fam == other_name_no_fam; + } + + return sex == other.sex && names_pass && dates_pass; } void Person::displayInfo()const diff --git a/src/person.hpp b/src/person.hpp index 3112197..205914f 100644 --- a/src/person.hpp +++ b/src/person.hpp @@ -7,19 +7,17 @@ enum ZoomLevel: U8; +enum: I16 { UNKNOWN_DATE=0 }; + struct EventTime { - enum: I16 { UNKNOWN_DATE=0 }; - enum: I8 { UNKNOWN_TIME=-1 }; - EventTime(I16 Year=UNKNOWN_DATE, U8 Month=UNKNOWN_DATE, U16 Day=UNKNOWN_DATE, I8 Hour=UNKNOWN_TIME, I8 Minute=UNKNOWN_TIME); + EventTime(I16 Year=UNKNOWN_DATE, U8 Month=UNKNOWN_DATE, U16 Day=UNKNOWN_DATE); void print(WINDOW*) const; I16 year; //The year in relation to Chritst's birth - 1 (AD) is the year He was born, -1 (BC) is the previous year. There is no year 0 U8 month; U16 day; - I8 hour; //0-23 - I8 minute; //0-59 }; enum Sex: U8 @@ -44,13 +42,12 @@ class Person { public: Person() = default; - Person(const char* aName, EventTime aBirth={}, Sex=M, EventTime aDeath={}); - /* Person(Person&&) = default; */ - /* Person& operator=(Person&&) = default; */ - /* Person& operator=(const Person&) = default; */ + Person(const char* aName, Sex=M, EventTime aBirth={}, EventTime aDeath={}); - bool operator==(const Person &other) const; + /* Are the two very likely the same person based on sex, name, dates */ + bool likelySame(const Person& other) const; + /* Display the person's info on the screen */ void displayInfo() const; /* Draw a Person's box on the terminal, as a part of the focused tree @@ -70,8 +67,8 @@ public: U16 drawAsSpouse(I16 drawY, I16 drawX, bool selected, bool hasTree, ZoomLevel) const; std::string name; - EventTime birth; Sex sex; + EventTime birth; EventTime death; private: diff --git a/src/tree.cpp b/src/tree.cpp index 59e9585..d91e8ec 100644 --- a/src/tree.cpp +++ b/src/tree.cpp @@ -26,7 +26,7 @@ Tree& Tree::operator+=(const Tree& other) { for (j = 0; j < initNum; ++j) { - if (other.people_[i] == people_[j]) + if (other.people_[i].likelySame(people_[j])) { newId[i] = j; break; @@ -87,7 +87,7 @@ Tree& Tree::operator-= (const Tree& other) { for (const Person& othPers: other.people_) { - if (people_[i] == othPers) + if (people_[i].likelySame(othPers)) { removePerson(i); --i; @@ -261,7 +261,7 @@ const std::vector& Tree::findRelations(person_id id) const void Tree::addPerson(const char* name, Sex sex, unsigned father, unsigned mother, EventTime birth, EventTime death) { - people_.emplace_back(name, birth, sex, death); + people_.emplace_back(name, sex, birth, death); relations_.emplace_back(); /* relations of the new person */