Compare commits
No commits in common. "66693d29637bc11ce93a70327fe160e1f4e21689" and "8eff3208fcc095c9bb429182d8ec847ba55bc068" have entirely different histories.
66693d2963
...
8eff3208fc
177
metro.cpp
177
metro.cpp
|
@ -1,177 +0,0 @@
|
|||
#include <sstream>
|
||||
#include <string>
|
||||
#include <algorithm>
|
||||
#include <map>
|
||||
#include <set>
|
||||
#include <list>
|
||||
#include <deque>
|
||||
#include <queue>
|
||||
#include <stack>
|
||||
#include <cassert>
|
||||
#include <memory>
|
||||
using namespace std;
|
||||
|
||||
// https://fit-wiki.cz/%C5%A1kola/p%C5%99edm%C4%9Bty/bi-pa2/pa2_zkou%C5%A1ka_2019-05-23
|
||||
|
||||
class CMHD {
|
||||
using Stop = int;
|
||||
struct Line {
|
||||
std::vector<Stop> _s;
|
||||
};
|
||||
using ALine = std::shared_ptr<Line>;
|
||||
|
||||
|
||||
public:
|
||||
void Add ( istringstream & is )
|
||||
{
|
||||
ALine l(new Line());
|
||||
|
||||
string str;
|
||||
while ( getline(is, str) ) {
|
||||
Stop s = addStop(str);
|
||||
_lines[s].push_back(l);
|
||||
l->_s.push_back(s);
|
||||
}
|
||||
}
|
||||
|
||||
//===============================================================================
|
||||
|
||||
set < string > Dest ( const string & from, int maxCost ) const {
|
||||
Stop start = findStop(from);
|
||||
if (start == -1)
|
||||
return { "unknown" };
|
||||
|
||||
std::set< std::string > ret;
|
||||
std::map< ALine, int > d;
|
||||
std::queue< ALine > q;
|
||||
|
||||
for (const auto& i : _lines[start]) {
|
||||
d[i] = 0;
|
||||
q.emplace(i);
|
||||
}
|
||||
|
||||
while (q.size()) {
|
||||
auto i = q.front();
|
||||
q.pop();
|
||||
|
||||
if (d[i] > maxCost) continue;
|
||||
|
||||
for (Stop s : i->_s) {
|
||||
ret.emplace( _names[s] );
|
||||
for ( const ALine& l : _lines[s]) {
|
||||
auto it = d.try_emplace(l, d[i] + 1);
|
||||
if (it.second) {
|
||||
q.emplace(l);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
//===============================================================================
|
||||
private:
|
||||
|
||||
inline Stop addStop( const std::string& s ) {
|
||||
auto it = _stops.try_emplace(s, _stops.size());
|
||||
if (it.second) {
|
||||
_names.emplace_back(s);
|
||||
_lines.emplace_back();
|
||||
}
|
||||
return it.first->second;
|
||||
};
|
||||
|
||||
inline Stop findStop( const std::string& s ) const {
|
||||
auto it = _stops.find(s);
|
||||
return it == _stops.end() ? -1 : it->second;
|
||||
};
|
||||
|
||||
// str -> stop
|
||||
std::map< std::string, Stop > _stops;
|
||||
|
||||
// stop -> str
|
||||
std::vector< std::string > _names;
|
||||
|
||||
// stop -> lines
|
||||
std::vector< std::vector < ALine > > _lines;
|
||||
};
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
int main ( void )
|
||||
{
|
||||
CMHD city;
|
||||
istringstream iss;
|
||||
iss.clear();
|
||||
|
||||
iss . str ( "A\nB\nC\nD\nE\n" );
|
||||
city . Add ( iss );
|
||||
iss . clear();
|
||||
|
||||
iss . str ( "B\nC\nF\nH\n" );
|
||||
city . Add ( iss );
|
||||
iss . clear();
|
||||
|
||||
iss . str ( "F\nG\nI\nJ\nK\nN\n" );
|
||||
city . Add ( iss );
|
||||
iss . clear();
|
||||
|
||||
iss . str ( "H\nL\n" );
|
||||
city . Add ( iss );
|
||||
iss . clear();
|
||||
|
||||
iss . str ( "L\nM\nN\nO\n" );
|
||||
city . Add ( iss );
|
||||
iss . clear();
|
||||
|
||||
iss . str ( "P\nQ\nR\nN\nS" );
|
||||
city . Add ( iss );
|
||||
iss . clear();
|
||||
|
||||
assert ( city . Dest ( "S", 0 ) == set < string > ( {"S", "N", "R", "Q", "P"} ) );
|
||||
|
||||
assert ( city . Dest ( "S", 1 ) == set < string > ( { "S", "N", "R", "Q", "P",
|
||||
"O", "M", "L",
|
||||
"K", "J", "I", "G", "F" } ) );
|
||||
|
||||
assert ( city . Dest ( "N", 0 ) == set < string > ( { "S", "N", "R", "Q", "P",
|
||||
"O", "M", "L",
|
||||
"K", "J", "I", "G", "F" } ) );
|
||||
|
||||
assert ( city . Dest ( "N", 1 ) == set < string > ( { "S", "N", "R", "Q", "P",
|
||||
"O", "M", "L",
|
||||
"K", "J", "I", "G", "F",
|
||||
"H", "F", "C", "B" } ) );
|
||||
|
||||
assert ( city . Dest ( "N", 2 ) == set < string > ( { "S", "N", "R", "Q", "P",
|
||||
"O", "M", "L",
|
||||
"K", "J", "I", "G", "F",
|
||||
"H", "F", "C", "B",
|
||||
"A", "D", "E" } ) );
|
||||
|
||||
assert ( city . Dest ( "unknown", 0 ) == set < string > ( { "unknown" } ) );
|
||||
assert ( city . Dest ( "unknown", 1 ) == set < string > ( { "unknown" } ) );
|
||||
assert ( city . Dest ( "unknown", 2 ) == set < string > ( { "unknown" }) );
|
||||
|
||||
return 0;
|
||||
}
|
301
set.cpp
301
set.cpp
|
@ -1,301 +0,0 @@
|
|||
/**
|
||||
* Implementujte metodu insert (vkládání), erase (mazání prvků
|
||||
* ze stromu a zároveň je potřeba uchovat správné pořádí podle
|
||||
* data vkládání) a vlastní destruktor, ostatní metody jsou
|
||||
* naimplentované. Kopírující konstruktor i operátor přiřazení
|
||||
* zakázán. Není povolené si přidat žádnou členskou proměnnou,
|
||||
* ale lze naimplementovat vlastní pomocné metody.
|
||||
*
|
||||
* Za správnost šablony neručím :-).
|
||||
*/
|
||||
|
||||
#include <string>
|
||||
#include <cassert>
|
||||
|
||||
// https://fit-wiki.cz/%C5%A1kola/p%C5%99edm%C4%9Bty/bi-pa2/pa2_zkou%C5%A1ka_2022-06-16
|
||||
|
||||
using namespace std;
|
||||
|
||||
class CTree
|
||||
{
|
||||
public:
|
||||
CTree() = default;
|
||||
~CTree() {
|
||||
CNode* i = m_First;
|
||||
while (i) {
|
||||
CNode* j = i->m_NextOrder;
|
||||
delete i;
|
||||
i = j;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
CTree(const CTree &src) = delete;
|
||||
|
||||
bool operator=(const CTree &other) = delete;
|
||||
|
||||
bool isSet(string key) {
|
||||
CNode * n = m_Root;
|
||||
while (n) {
|
||||
if (key == n->m_Key)
|
||||
return true;
|
||||
else if (key > n->m_Key)
|
||||
n = n->m_R;
|
||||
else
|
||||
n = n->m_L;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool insert(string key) {
|
||||
if (!m_Root)
|
||||
return m_Root = m_First = m_Last = new CNode(key);
|
||||
|
||||
CNode* i = nullptr;
|
||||
CNode* n = m_Root;
|
||||
while (n) {
|
||||
if (key == n->m_Key) {
|
||||
return false;
|
||||
} else if (key > n->m_Key) {
|
||||
i = n;
|
||||
n = n->m_R;
|
||||
} else {
|
||||
i = n;
|
||||
n = n->m_L;
|
||||
}
|
||||
}
|
||||
|
||||
n = new CNode(key);
|
||||
if (key > i->m_Key)
|
||||
i->m_R = n;
|
||||
else
|
||||
i->m_L = n;
|
||||
|
||||
n->m_PrevOrder = m_Last;
|
||||
m_Last = m_Last->m_NextOrder = n;
|
||||
return true;
|
||||
}
|
||||
|
||||
bool erase(string key) {
|
||||
CNode** p = &m_Root;
|
||||
CNode* n = m_Root;
|
||||
while (n) {
|
||||
if (key == n->m_Key)
|
||||
goto found;
|
||||
else if (key > n->m_Key) {
|
||||
p = &n->m_R;
|
||||
n = n->m_R;
|
||||
} else {
|
||||
p = &n->m_L;
|
||||
n = n->m_L;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
|
||||
found:
|
||||
if (!(n->m_L && n->m_R)) { // one or none child
|
||||
*p = (CNode*)((ptrdiff_t)n->m_L | (ptrdiff_t)n->m_R);
|
||||
} else {
|
||||
CNode* ts = n->m_L;
|
||||
CNode** tsp = &n->m_L;
|
||||
while (ts->m_R) {
|
||||
tsp = &ts->m_R;
|
||||
ts = ts->m_R;
|
||||
}
|
||||
swapTree( n, ts );
|
||||
*tsp = ts->m_L;
|
||||
n = ts;
|
||||
}
|
||||
eraseList(n);
|
||||
delete n;
|
||||
return true;
|
||||
}
|
||||
|
||||
protected:
|
||||
class CNode {
|
||||
public:
|
||||
CNode(string key) : m_Key(key) {}
|
||||
string m_Key;
|
||||
CNode * m_L = nullptr;
|
||||
CNode * m_R = nullptr;
|
||||
CNode * m_PrevOrder = nullptr;
|
||||
CNode * m_NextOrder = nullptr;
|
||||
};
|
||||
CNode * m_Root = nullptr;
|
||||
CNode * m_First = nullptr;
|
||||
CNode * m_Last = nullptr;
|
||||
|
||||
void swapTree( CNode* a, CNode* b ) {
|
||||
if (a == m_Last) m_Last = b;
|
||||
else if (b == m_Last) m_Last = a;
|
||||
|
||||
if (a == m_First) m_First = b;
|
||||
else if (b == m_First) m_First = a;
|
||||
|
||||
if (a->m_NextOrder) a->m_NextOrder->m_PrevOrder = b;
|
||||
if (a->m_PrevOrder) a->m_PrevOrder->m_NextOrder = b;
|
||||
if (b->m_NextOrder) b->m_NextOrder->m_PrevOrder = a;
|
||||
if (b->m_PrevOrder) b->m_PrevOrder->m_NextOrder = a;
|
||||
|
||||
std::swap(a->m_NextOrder, b->m_NextOrder);
|
||||
std::swap(a->m_PrevOrder, b->m_PrevOrder);
|
||||
std::swap(a->m_Key, b->m_Key);
|
||||
}
|
||||
|
||||
void eraseList( CNode* a ) {
|
||||
if (a->m_PrevOrder)
|
||||
a->m_PrevOrder->m_NextOrder = a->m_NextOrder;
|
||||
else
|
||||
m_First = a->m_NextOrder;
|
||||
|
||||
if (a->m_NextOrder)
|
||||
a->m_NextOrder->m_PrevOrder = a->m_PrevOrder;
|
||||
else
|
||||
m_Last = a->m_PrevOrder;
|
||||
}
|
||||
};
|
||||
|
||||
class CTester : public CTree
|
||||
{
|
||||
public:
|
||||
CTester () = default;
|
||||
void test()
|
||||
{
|
||||
CTester t0;
|
||||
assert(t0.insert("PA1")==true);
|
||||
assert(t0.m_First->m_Key=="PA1" && t0.m_First->m_NextOrder == nullptr);
|
||||
assert(t0.isSet("PA1")==true);
|
||||
assert(t0.insert("UOS")==true);
|
||||
assert(t0.insert("PA2")==true);
|
||||
assert(t0.isSet("PA2")==true);
|
||||
assert(t0.isSet("PA3")==false);
|
||||
|
||||
assert(t0.insert("PA2")==false);
|
||||
assert(t0.insert("CAO")==true);
|
||||
assert(t0.insert("LIN")==true);
|
||||
assert(t0.insert("AAG")==true);
|
||||
assert(t0.insert("AG1")==true);
|
||||
assert(t0.insert("ZDM")==true);
|
||||
|
||||
assert(t0.m_First->m_Key == "PA1"
|
||||
&& t0.m_First->m_NextOrder->m_Key == "UOS"
|
||||
&& t0.m_First->m_NextOrder->m_NextOrder->m_Key == "PA2"
|
||||
&& t0.m_First->m_NextOrder->m_NextOrder->m_NextOrder->m_Key == "CAO"
|
||||
&& t0.m_First->m_NextOrder->m_NextOrder->m_NextOrder->m_NextOrder->m_Key == "LIN"
|
||||
&& t0.m_First->m_NextOrder->m_NextOrder->m_NextOrder->m_NextOrder->m_NextOrder->m_Key == "AAG"
|
||||
&& t0.m_First->m_NextOrder->m_NextOrder->m_NextOrder->m_NextOrder->m_NextOrder->m_NextOrder->m_Key == "AG1"
|
||||
&& t0.m_First->m_NextOrder->m_NextOrder->m_NextOrder->m_NextOrder->m_NextOrder->m_NextOrder->m_NextOrder->m_Key == "ZDM");
|
||||
|
||||
assert(t0.m_Last->m_Key == "ZDM"
|
||||
&& t0.m_Last->m_PrevOrder->m_Key == "AG1"
|
||||
&& t0.m_Last->m_PrevOrder->m_PrevOrder->m_Key == "AAG"
|
||||
&& t0.m_Last->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_Key == "LIN"
|
||||
&& t0.m_Last->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_Key == "CAO"
|
||||
&& t0.m_Last->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_Key == "PA2"
|
||||
&& t0.m_Last->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_Key == "UOS"
|
||||
&& t0.m_Last->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_Key == "PA1");
|
||||
|
||||
assert(t0.erase("")==false);
|
||||
|
||||
assert(t0.erase("ZDM")==true);
|
||||
assert(t0.m_First->m_Key == "PA1"
|
||||
&& t0.m_First->m_NextOrder->m_Key == "UOS"
|
||||
&& t0.m_First->m_NextOrder->m_NextOrder->m_Key == "PA2"
|
||||
&& t0.m_First->m_NextOrder->m_NextOrder->m_NextOrder->m_Key == "CAO"
|
||||
&& t0.m_First->m_NextOrder->m_NextOrder->m_NextOrder->m_NextOrder->m_Key == "LIN"
|
||||
&& t0.m_First->m_NextOrder->m_NextOrder->m_NextOrder->m_NextOrder->m_NextOrder->m_Key == "AAG"
|
||||
&& t0.m_First->m_NextOrder->m_NextOrder->m_NextOrder->m_NextOrder->m_NextOrder->m_NextOrder->m_Key == "AG1");
|
||||
assert(t0.m_Last->m_Key == "AG1"
|
||||
&& t0.m_Last->m_PrevOrder->m_Key == "AAG"
|
||||
&& t0.m_Last->m_PrevOrder->m_PrevOrder->m_Key == "LIN"
|
||||
&& t0.m_Last->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_Key == "CAO"
|
||||
&& t0.m_Last->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_Key == "PA2"
|
||||
&& t0.m_Last->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_Key == "UOS"
|
||||
&& t0.m_Last->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_Key == "PA1");
|
||||
assert(t0.isSet("ZDM")==false);
|
||||
|
||||
assert(t0.erase("AAG")==true);
|
||||
assert(t0.m_First->m_Key == "PA1"
|
||||
&& t0.m_First->m_NextOrder->m_Key == "UOS"
|
||||
&& t0.m_First->m_NextOrder->m_NextOrder->m_Key == "PA2"
|
||||
&& t0.m_First->m_NextOrder->m_NextOrder->m_NextOrder->m_Key == "CAO"
|
||||
&& t0.m_First->m_NextOrder->m_NextOrder->m_NextOrder->m_NextOrder->m_Key == "LIN"
|
||||
&& t0.m_First->m_NextOrder->m_NextOrder->m_NextOrder->m_NextOrder->m_NextOrder->m_Key == "AG1");
|
||||
assert(t0.m_Last->m_Key == "AG1"
|
||||
&& t0.m_Last->m_PrevOrder->m_Key == "LIN"
|
||||
&& t0.m_Last->m_PrevOrder->m_PrevOrder->m_Key == "CAO"
|
||||
&& t0.m_Last->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_Key == "PA2"
|
||||
&& t0.m_Last->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_Key == "UOS"
|
||||
&& t0.m_Last->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_Key == "PA1");
|
||||
assert(t0.isSet("AAG")==false);
|
||||
|
||||
assert(t0.erase("CAO")==true);
|
||||
assert(t0.m_First->m_Key == "PA1"
|
||||
&& t0.m_First->m_NextOrder->m_Key == "UOS"
|
||||
&& t0.m_First->m_NextOrder->m_NextOrder->m_Key == "PA2"
|
||||
&& t0.m_First->m_NextOrder->m_NextOrder->m_NextOrder->m_Key == "LIN"
|
||||
&& t0.m_First->m_NextOrder->m_NextOrder->m_NextOrder->m_NextOrder->m_Key == "AG1");
|
||||
assert(t0.m_Last->m_Key == "AG1"
|
||||
&& t0.m_Last->m_PrevOrder->m_Key == "LIN"
|
||||
&& t0.m_Last->m_PrevOrder->m_PrevOrder->m_Key == "PA2"
|
||||
&& t0.m_Last->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_Key == "UOS"
|
||||
&& t0.m_Last->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_Key == "PA1");
|
||||
assert(t0.isSet("CAO")==false);
|
||||
|
||||
assert(t0.erase("UOS")==true);
|
||||
assert(t0.m_First->m_Key == "PA1"
|
||||
&& t0.m_First->m_NextOrder->m_Key == "PA2"
|
||||
&& t0.m_First->m_NextOrder->m_NextOrder->m_Key == "LIN"
|
||||
&& t0.m_First->m_NextOrder->m_NextOrder->m_NextOrder->m_Key == "AG1");
|
||||
assert(t0.m_Last->m_Key == "AG1"
|
||||
&& t0.m_Last->m_PrevOrder->m_Key == "LIN"
|
||||
&& t0.m_Last->m_PrevOrder->m_PrevOrder->m_Key == "PA2"
|
||||
&& t0.m_Last->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_Key == "PA1");
|
||||
assert(t0.isSet("UOS")==false);
|
||||
|
||||
assert(t0.erase("UOS")==false);
|
||||
assert(t0.m_First->m_Key == "PA1"
|
||||
&& t0.m_First->m_NextOrder->m_Key == "PA2"
|
||||
&& t0.m_First->m_NextOrder->m_NextOrder->m_Key == "LIN"
|
||||
&& t0.m_First->m_NextOrder->m_NextOrder->m_NextOrder->m_Key == "AG1");
|
||||
assert(t0.m_Last->m_Key == "AG1"
|
||||
&& t0.m_Last->m_PrevOrder->m_Key == "LIN"
|
||||
&& t0.m_Last->m_PrevOrder->m_PrevOrder->m_Key == "PA2"
|
||||
&& t0.m_Last->m_PrevOrder->m_PrevOrder->m_PrevOrder->m_Key == "PA1");
|
||||
assert(t0.isSet("UOS")==false);
|
||||
|
||||
assert(t0.erase("LIN")==true);
|
||||
assert(t0.m_First->m_Key == "PA1"
|
||||
&& t0.m_First->m_NextOrder->m_Key == "PA2"
|
||||
&& t0.m_First->m_NextOrder->m_NextOrder->m_Key == "AG1");
|
||||
assert(t0.m_Last->m_Key == "AG1"
|
||||
&& t0.m_Last->m_PrevOrder->m_Key == "PA2"
|
||||
&& t0.m_Last->m_PrevOrder->m_PrevOrder->m_Key == "PA1");
|
||||
assert(t0.isSet("LIN")==false);
|
||||
|
||||
assert(t0.erase("PA1")==true);
|
||||
assert(t0.m_First->m_Key == "PA2"
|
||||
&& t0.m_First->m_NextOrder->m_Key == "AG1");
|
||||
assert(t0.m_Last->m_Key == "AG1"
|
||||
&& t0.m_Last->m_PrevOrder->m_Key == "PA2");
|
||||
assert(t0.isSet("PA1")==false);
|
||||
|
||||
assert(t0.erase("PA2")==true);
|
||||
assert(t0.m_First->m_Key == "AG1");
|
||||
assert(t0.m_Last->m_Key == "AG1");
|
||||
assert(t0.isSet("PA2")==false);
|
||||
|
||||
assert(t0.erase("AG1")==true);
|
||||
assert(t0.m_First == t0.m_Last);
|
||||
assert(t0.isSet("AG1")==false);
|
||||
}
|
||||
};
|
||||
#include <iostream>
|
||||
int main ( )
|
||||
{
|
||||
CTester t;
|
||||
t.test();
|
||||
std::cout << "success!\n";
|
||||
return EXIT_SUCCESS;
|
||||
}
|
Loading…
Reference in New Issue