card_path.cpp 19 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005
  1. #include <stdio.h>
  2. #include <algorithm>
  3. #include <unordered_map>
  4. #include <set>
  5. #include <memory>
  6. #include <atomic>
  7. #include <thread>
  8. #include <list>
  9. #include "zlist.h"
  10. #include "line.h"
  11. #include "ant.h"
  12. #include "config_file.h"
  13. #include "card_path.h"
  14. #include "visit.h"
  15. namespace{
  16. //static const double PI = 3.1415926;
  17. //static const double TPI = 2*PI;
  18. inline bool eq(double a,double b,double e=0.0001)
  19. {
  20. return fabs(a-b)<e;
  21. }
  22. struct vertex:point
  23. {
  24. float level;
  25. int sid0,sid1;
  26. vertex()
  27. :level(0)
  28. ,sid0(0)
  29. ,sid1(0)
  30. {}
  31. vertex(const point&pt,float level_=0,int site_id0=0,int site_id1=0)
  32. :point(pt)
  33. ,level(level_)
  34. ,sid0(site_id0)
  35. ,sid1(site_id1)
  36. {
  37. }
  38. std::string to_string()const
  39. {
  40. char buf[128];
  41. sprintf(buf,"%.2f,%.3lf,%d,%d,%.2lf",x,y,sid0,sid1,level/PI*180);
  42. return buf;
  43. }
  44. };
  45. struct vertex_list;
  46. struct base_path:std::array<int,2>
  47. {
  48. int sid;
  49. base_path(int i1=-1,int i2=-1,int _sid=0)
  50. {
  51. at(0)=i1;
  52. at(1)=i2;
  53. sid=_sid;
  54. }
  55. bool operator<(const base_path&o)const
  56. {
  57. int c=at(0)-o.at(0);
  58. if(c!=0)
  59. return c<0;
  60. return at(1)-o.at(1)<0;
  61. }
  62. point cross(const vertex_list&v_list, const base_path&o)const;
  63. bool contains(const vertex_list&v_list, const point&o, double e)const;
  64. double arg(const vertex_list&v)const;
  65. int type(const vertex_list&v)const;
  66. line_v as_line(const vertex_list&v)const;
  67. int level(const vertex_list&v)const;
  68. };
  69. struct vertex_list
  70. {
  71. std::vector<vertex> v;
  72. std::string to_string()const
  73. {
  74. std::string ret;
  75. ret.reserve(1024);
  76. char buf[128];
  77. for(int i=0,len=v.size();i<len;i++)
  78. {
  79. sprintf(buf,"vertex:%3d,%s\n",i,v[i].to_string().c_str());
  80. ret+=buf;
  81. }
  82. return std::move(ret);
  83. }
  84. void log()
  85. {
  86. log_info("%s",to_string().c_str());
  87. }
  88. static unsigned hash(const point&p)
  89. {
  90. return (((((unsigned)p.x)>>2)<<16) + (((unsigned)p.y)>>2));
  91. }
  92. int find(const point&p,double x=0.01)const
  93. {
  94. int rc=-1;
  95. double t;
  96. for(int i=0,len=v.size();i<len;i++)
  97. {
  98. t=p.dist(v[i]);
  99. if(t<x)
  100. {
  101. rc=i;
  102. x=t;
  103. }
  104. }
  105. return rc;
  106. }
  107. int add(const point&p,float level=0,int sid0=0,int sid1=0)
  108. {
  109. int i=find(p);
  110. if(i<0)
  111. {
  112. v.push_back(vertex(p,level,sid0,sid1));
  113. return v.size()-1;
  114. }
  115. vertex&v0=v[i];
  116. v0.level=std::max(v0.level,level);
  117. return i;
  118. }
  119. int size()const
  120. {
  121. return v.size();
  122. }
  123. const vertex&operator[](int i)const
  124. {
  125. return v[i];
  126. }
  127. vertex&operator[](int i)
  128. {
  129. return v[i];
  130. }
  131. };
  132. int base_path::level(const vertex_list&v)const
  133. {
  134. const vertex&p0=v[at(0)];
  135. const vertex&p1=v[at(1)];
  136. return p0.level+p1.level;
  137. }
  138. line_v base_path::as_line(const vertex_list&v)const
  139. {
  140. const vertex&p0=v[at(0)];
  141. const vertex&p1=v[at(1)];
  142. return line_v(p0,p1);
  143. }
  144. double base_path::arg(const vertex_list&v)const
  145. {
  146. return as_line(v).arg();
  147. }
  148. bool base_path::contains(const vertex_list&v, const point&o, double e)const
  149. {
  150. return as_line(v).contain(o,e);
  151. }
  152. point base_path::cross(const vertex_list&v, const base_path&o)const
  153. {
  154. line_v l0=as_line(v);
  155. line_v l1=o.as_line(v);
  156. return l0.crossing(l1);
  157. }
  158. void log_path(const std::vector<base_path>&path,const vertex_list&v_list,const char*add_info="")
  159. {
  160. log_info("%s\n","----------------------------------------------------------------");
  161. for(int i=0,len=path.size();i<len;i++)
  162. {
  163. double c=path[i].arg(v_list)/PI*180;
  164. log_info("base_path:%s %.6lf, %03d,(%d,%s),(%d,%s)",add_info,c,i,path[i][0],v_list[path[i][0]].to_string().c_str(),path[i][1],v_list[path[i][1]].to_string().c_str());
  165. }
  166. }
  167. struct handle_path :visitor<std::shared_ptr<site>>
  168. {
  169. std::vector<base_path> ret;
  170. vertex_list v;
  171. handle_path()
  172. {
  173. v.add(point(0,0),0,-1);
  174. }
  175. bool visit(std::shared_ptr<site> sit)
  176. {
  177. //auto&s=sites[i];
  178. const auto &s = *sit;
  179. if(!s.have_valid_path())
  180. return false;
  181. if(s.path(0).empty()||s.path(1).empty())
  182. return false;
  183. if(s[0].size()<2)
  184. return false;
  185. line_v l000 = s[0][0][0]; //天线->分站天线路径集合->路径
  186. line_v l010 = s[0][1][0];
  187. if(l000.is_same(l010))
  188. {
  189. int p0=v.add(point::min(s.path(0),s.path(1)),0,s.m_id);
  190. int p1=v.add(point::max(s.path(0),s.path(1)),0,s.m_id);
  191. ret.push_back(base_path(p0,p1));
  192. ret.back().sid=s.m_id;
  193. }
  194. else
  195. {
  196. point px = l000.line::crossing(l010);
  197. for(int i=0;i<2;i++)
  198. {
  199. int p0=v.add(point::min(px,s.path(i)),0,s.m_id);
  200. int p1=v.add(point::max(px,s.path(i)),0,s.m_id);
  201. ret.push_back(base_path(p0,p1));
  202. ret.back().sid=s.m_id;
  203. }
  204. }
  205. for(int i=0;i<2;i++)
  206. {
  207. if(!s[0][i][1].empty())
  208. {
  209. int p0=v.add(point::min(s[0][i][1][0],s[0][i][1][1]),0,s.m_id);
  210. int p1=v.add(point::max(s[0][i][1][0],s[0][i][1][1]),0,s.m_id);
  211. ret.push_back(base_path(p0,p1));
  212. ret.back().sid=s.m_id;
  213. }
  214. }
  215. return true;
  216. }
  217. };
  218. static std::vector<base_path> init_path(std::vector<base_path> & ret,vertex_list&v)
  219. {
  220. do
  221. {
  222. config_file cfg;
  223. if(cfg.open("../etc/path-not-cross.ini"))
  224. break;
  225. auto kset=cfg.keys();
  226. if(kset.empty())
  227. break;
  228. for(auto k:kset)
  229. {
  230. if(strncmp(k,"add_path",8)!=0)
  231. continue;
  232. const char* vv=cfg.get(k,"");
  233. point p0;
  234. point p1;
  235. if(sscanf(vv,"%lf,%lf,%lf,%lf",&p0.x,&p0.y,&p1.x,&p1.y)==4)
  236. {
  237. point p_0=point::min(p0,p1);
  238. point p_1=point::max(p0,p1);
  239. int p00=v.add(p_0,0,0);
  240. int p10=v.add(p_1,0,0);
  241. ret.push_back(base_path(p00,p10,0));
  242. }
  243. }
  244. break;
  245. }while(1);
  246. auto remove_dup=[](std::vector<base_path>&ret){
  247. std::sort(ret.begin(),ret.end());
  248. ret.erase(std::unique(ret.begin(),ret.end()),ret.end());
  249. };
  250. auto remove_empty=[](std::vector<base_path>&ret,vertex_list&v){
  251. ret.erase(std::remove_if(ret.begin(),ret.end(),[&v](base_path&p){
  252. point&p0=v[p[0]];
  253. point&p1=v[p[1]];
  254. return p0.dist(p1)<.00001;
  255. }),
  256. ret.end());
  257. };
  258. auto sort_path=[](std::vector<base_path> & ret,vertex_list&v){
  259. std::sort(ret.begin(),ret.end(),[&v](const base_path&p1,const base_path&p2){
  260. return point::min(v[p1[0]],v[p1[1]]) < point::min(v[p2[0]],v[p2[1]]);
  261. });
  262. };
  263. remove_dup(ret);
  264. sort_path(ret,v);
  265. log_path(ret,v,"合并前");
  266. //合并相同
  267. for(int i=0,len=ret.size();i<len;i++)
  268. {
  269. line_v li=ret[i].as_line(v);
  270. for(int j=i+1;j<len;j++)
  271. {
  272. line_v lj=ret[j].as_line(v);
  273. if(!lj.is_same(li,1)) //li线段两个点在lj直线上
  274. continue;
  275. line_v ij=lj.projection(li);//重叠
  276. if(ij.empty()&&ij[0].empty()&&ij[0].empty())
  277. continue;
  278. point p0=li.as_line().projection(v[ret[j][0]]);
  279. point p1=li.as_line().projection(v[ret[j][1]]);
  280. p0=point::min(p0,v[ret[i][0]]);
  281. p1=point::max(p1,v[ret[i][1]]);
  282. ret[j][0]=v.add(p0,0);
  283. ret[j][1]=v.add(p1,0);
  284. ret[i][0]=0;
  285. ret[i][1]=0;
  286. break;
  287. }
  288. }
  289. ret.erase(std::remove_if(ret.begin(),ret.end(),[&v](const base_path&p){
  290. return p[0]==0||p[1]==0;
  291. }),ret.end());
  292. sort_path(ret,v);
  293. log_path(ret,v,"合并后");
  294. //非路径交点配置
  295. std::vector<point> no_cross;
  296. auto in_no_cross=[&no_cross](const point&pt){
  297. for(auto p:no_cross)
  298. {
  299. if(p.dist(pt)<3)
  300. return true;
  301. }
  302. return false;
  303. };
  304. do
  305. {
  306. config_file cfg;
  307. if(cfg.open("../etc/path-not-cross.ini"))
  308. break;
  309. auto kset=cfg.keys();
  310. if(kset.empty())
  311. break;
  312. for(auto k:kset)
  313. {
  314. if(strncmp(k,"pt",2)!=0)
  315. continue;
  316. const char* v=cfg.get(k,"");
  317. point tmp;
  318. if(sscanf(v,"%lf,%lf",&tmp.x,&tmp.y)==2)
  319. no_cross.push_back(tmp);
  320. }
  321. for(auto p:no_cross)
  322. {
  323. log_info("no_cross_point:x=%lf,y=%lf",p.x,p.y);
  324. }
  325. break;
  326. }while(1);
  327. std::vector<std::vector<int>> p0(ret.size());
  328. std::vector<base_path> ret2;
  329. for(int i=0,len=ret.size();i<len;i++)
  330. {
  331. p0[i].push_back(ret[i][0]);
  332. for(int j=i+1;j<len;j++)
  333. {
  334. if(i==j) continue;
  335. point cr=ret[i].cross(v,ret[j]);
  336. if(cr.empty())
  337. continue;
  338. if(in_no_cross(cr))
  339. continue;
  340. double arg=fabs(ret[i].as_line(v).arg()-ret[j].as_line(v).arg());
  341. while(arg>PI/2)
  342. arg=PI-arg;
  343. if(arg/PI*180<5)//相交小于5度,不切分已有路径
  344. continue;
  345. int id=v.add(cr,arg,v[ret[i][0]].sid0,v[ret[j][0]].sid0);
  346. p0[i].push_back(id);
  347. p0[j].push_back(id);
  348. }
  349. p0[i].push_back(ret[i][1]);
  350. std::sort(p0[i].begin(),p0[i].end(),[&v](int i0,int i1){ return v[i0]<v[i1]; });
  351. #if 0
  352. if(p0[i].size())
  353. {
  354. for(int v=0;v<2;v++)
  355. {
  356. if(v[ret[i][v]].dist(v[p0[i].front()])<3)
  357. continue;
  358. if(v[ret[i][v]].dist(v[p0[i].back()])<3)
  359. continue;
  360. p0[i].push_back(ret[i][v]);
  361. std::sort(p0[i].begin(),p0[i].end(),[&v](int i0,int i1){ return v[i0]<v[i1]; });
  362. }
  363. }
  364. else
  365. {
  366. std::sort(p0[i].begin(),p0[i].end(),[&v](int i0,int i1){ return v[i0]<v[i1]; });
  367. }
  368. #endif
  369. auto it=std::unique(p0[i].begin(),p0[i].end());
  370. p0[i].erase(it,p0[i].end());
  371. for(int j=1,cnt=p0[i].size();j<cnt;j++)
  372. {
  373. ret2.push_back(base_path(p0[i][j - 1], p0[i][j]));
  374. ret2.back().sid = ret[i].sid;
  375. }
  376. }
  377. remove_empty(ret2,v);
  378. remove_dup(ret2);
  379. sort_path(ret,v);
  380. log_path(ret2,v,"拆分后");
  381. return std::move(ret2);
  382. }
  383. #if 0
  384. struct ghash
  385. {
  386. static std::tuple<int,int> decode(unsigned h)
  387. {
  388. const uint64_t S=0x8000000000000000;
  389. int x=0,y=0;
  390. for(int i=0;i<64;i++)
  391. {
  392. x<<=1;
  393. y<<=1;
  394. if(h&S)
  395. x|=1;
  396. h<<=1;
  397. if(h&S)
  398. y|=1;
  399. h<<=1;
  400. }
  401. return std::make_tuple(x-2147483648,y-2147483648);
  402. }
  403. static uint64_t encode(int64_t x, int64_t y)
  404. {
  405. return encode_(x+2147483648,y+2147483648);
  406. }
  407. public: //test
  408. static void test_code(int64_t x,int64_t y)
  409. {
  410. uint64_t h=ghash::encode(x,y);
  411. auto t=ghash::decode(h);
  412. printf("src x=%X,y=%X hash=%X,check x=%X,y=%X\n",x,y,h,std::get<0>(t),std::get<1>(t));
  413. }
  414. static void test()
  415. {
  416. for(int i=0;i<10;i++)
  417. {
  418. test_code((4<<i)-1,(4<<i)-1);
  419. test_code((4<<i)-1,(4<<i));
  420. test_code((4<<i)-1,(4<<i)-1);
  421. test_code((4<<i),(4<<i)-1);
  422. }
  423. }
  424. private:
  425. static unsigned encode_(unsigned short x, unsigned short y)
  426. {
  427. const unsigned S=0x8000;
  428. unsigned r=0;
  429. for(int i=0;i<16;i++)
  430. {
  431. r<<=2;
  432. if(x&S)
  433. {
  434. r|=(y&S)?3:2;
  435. }
  436. else
  437. {
  438. if(y&S) r|=1;
  439. }
  440. x<<=1;
  441. y<<=1;
  442. }
  443. return r;
  444. }
  445. };
  446. #endif
  447. struct geolist
  448. {
  449. std::unordered_map<uint64_t,int> geo2path;
  450. public:
  451. static uint64_t encode(double x0,double y0)
  452. {
  453. uint64_t x=(uint32_t)(x0*10);
  454. uint64_t y=(uint32_t)(y0*10);
  455. return (x<<32)|y;
  456. }
  457. int find(double x,double y)const
  458. {
  459. uint64_t h=encode(x,y);
  460. auto it=geo2path.find(h);
  461. if(it==geo2path.end())
  462. return -1;
  463. return it->second;
  464. }
  465. void add(double x,double y,int id)
  466. {
  467. uint64_t h=encode(x,y);
  468. geo2path.insert(std::make_pair(h,id));
  469. }
  470. int size()
  471. {
  472. return geo2path.size();
  473. }
  474. void print()
  475. {
  476. for(auto it=geo2path.begin();it!=geo2path.end();++it)
  477. {
  478. //std::cout<<it->first<<"\n";
  479. printf("%ld\n",it->first);
  480. }
  481. }
  482. geolist()
  483. {
  484. }
  485. ~geolist()
  486. {
  487. }
  488. };
  489. struct graph
  490. {
  491. vertex_list v;
  492. std::vector<std::vector<int>> d; //索引为起始顶点,数组内容为目标点
  493. std::vector<std::array<int,2>> l; //bast_path list
  494. geolist geo;
  495. graph()
  496. {}
  497. void init(const vertex_list&v_,const std::vector<base_path>&bp)
  498. {
  499. for(auto&p:bp)
  500. {
  501. int from=v.add(v_[p[0]]);
  502. int to=v.add(v_[p[1]]);
  503. l.push_back({from,to});
  504. int id=l.size()-1;
  505. line_v lv(v[from],v[to]);
  506. log_info("graph::init() site:%d line:%s\n",p.sid, lv.to_string().c_str());
  507. double cos=lv.cos_k();
  508. double sin=lv.sin_k();
  509. double x,y;
  510. for(double r=0,len=lv.length();r<len+0.1;r+=0.05)
  511. {
  512. x=lv[0].x+r*cos;
  513. y=lv[0].y+r*sin;
  514. // printf("x=%lf,y=%lf\n",x,y);
  515. for(int i=-1;i<=1;i++)
  516. for(int j=-1;j<=1;j++)
  517. {
  518. geo.add(x+i/10.,y+j/10.,id);
  519. }
  520. }
  521. add(from,to);
  522. }
  523. }
  524. std::vector<line_v> find_possible_path(const point&from,double dist) const
  525. {
  526. std::vector<line_v> ret;
  527. int start_pt_id=v.find(from,dist);
  528. if(start_pt_id==-1)
  529. return std::move(ret);
  530. point start_pt=v[start_pt_id];
  531. for(uint32_t i=0;i<d[start_pt_id].size();i++)
  532. {
  533. ret.push_back(line_v(start_pt,v[d[start_pt_id][i]]));
  534. }
  535. return std::move(ret);
  536. }
  537. void add(int from,int to)
  538. {
  539. if((int)d.size()<=from) d.resize(from+1);
  540. if((int)d.size()<=to) d.resize(to+1);
  541. d[from].push_back(to);
  542. d[to].push_back(from);
  543. }
  544. bool find(std::vector<int>&ret,int from,std::array<int,2>&to,std::set<int>&ex,int level)
  545. {
  546. if(level--<0)
  547. return false;
  548. ret.push_back(from);
  549. for(int p:d[from]) //在当前路径
  550. {
  551. if(ex.find(p)!=ex.end()) //找过
  552. continue;
  553. if(p==to[0]||p==to[1])//找到
  554. return true;
  555. // {
  556. // ret.push_back(p);
  557. // return true;
  558. // }
  559. }
  560. ex.insert(from);
  561. for(int p:d[from])//在下级路径
  562. {
  563. if(ex.find(p)!=ex.end())//找过
  564. continue;
  565. if(find(ret,p,to,ex,level)) //找到
  566. {
  567. return true;
  568. }
  569. }
  570. ret.pop_back();
  571. return false;
  572. }
  573. bool is_at_path(const point&pt)const
  574. {
  575. return geo.find(pt.x,pt.y)>=0;
  576. }
  577. struct item
  578. {
  579. item(int _vid=-1, int _g=0,int _h=0,std::shared_ptr<item> _parent=nullptr)
  580. :vid(_vid)
  581. ,g(_g)
  582. ,h(_h)
  583. ,parent(_parent)
  584. {
  585. }
  586. int vid=-1,g=0,h=0;
  587. std::shared_ptr<item> parent;
  588. int cost()const {return g+h;}
  589. bool operator< (const item&i) const
  590. {
  591. return vid<i.vid;
  592. }
  593. };
  594. std::vector<point> find2(const point&from,const point&to)
  595. {
  596. int f=geo.find(from.x,from.y);
  597. int t=geo.find(to.x,to.y);
  598. if(f<0 || t<0 || f==t)
  599. return {};
  600. std::set<std::shared_ptr<item>> open_set;
  601. std::set<int> close_set;
  602. open_set.insert(std::make_shared<item>(l[f][0],from.dist(v[l[f][0]]),to.dist(v[l[f][0]])));
  603. open_set.insert(std::make_shared<item>(l[f][1],from.dist(v[l[f][1]]),to.dist(v[l[f][1]])));
  604. std::shared_ptr<item> cur;
  605. while(open_set.size()>0)
  606. {
  607. cur=*open_set.begin();
  608. for(auto&i:open_set)
  609. {
  610. if(i->cost()<cur->cost())
  611. cur=i;
  612. }
  613. open_set.erase(cur);
  614. close_set.insert(cur->vid);
  615. if(cur->vid==l[t][0]||cur->vid==l[t][1])
  616. break;
  617. for(auto vid:d[cur->vid])
  618. {
  619. if(close_set.find(vid)!=close_set.end())
  620. continue;
  621. open_set.insert(std::make_shared<item>(vid,cur->g+v[cur->vid].dist(v[vid]),to.dist(v[vid]),cur));
  622. }
  623. }
  624. if(open_set.size()==0)
  625. {
  626. return {};
  627. }
  628. std::vector<point> rc;
  629. while(cur.get())
  630. {
  631. rc.push_back(v[cur->vid]);
  632. cur=cur->parent;
  633. }
  634. std::reverse(rc.begin(),rc.end());
  635. rc.push_back(to);
  636. auto bp=from;
  637. auto it1=rc.begin();
  638. for(auto it2=it1+1;it1!=rc.end() && it2!=rc.end();it2++)
  639. {
  640. if(line(bp,*it1).dist(*it2)<0.1)
  641. {
  642. *it1=*it2;
  643. }
  644. else
  645. {
  646. bp=*it1++;
  647. *it1=*it2;
  648. }
  649. }
  650. rc.erase(it1,rc.end());
  651. if(rc.size() && from.dist(*rc.begin())<0.1)
  652. {
  653. rc.erase(rc.begin());
  654. }
  655. return std::move(rc);
  656. }
  657. std::vector<point> find(const point&from,const point&to)
  658. {
  659. int f=geo.find(from.x,from.y);
  660. int t=geo.find(to.x,to.y);
  661. if(f<0 || t<0 || f==t)
  662. return {};
  663. #if 0
  664. std::vector<point> rc[2];
  665. for(int i=0;i<2;i++)
  666. {
  667. std::vector<int> ret;
  668. std::set<int> ex({l[f][1-i]});
  669. if(find(ret,l[f][i],l[t],ex,2))
  670. {
  671. for(auto id:ret)
  672. rc[i].push_back(v[id]);
  673. }
  674. }
  675. if(!rc[0].empty() && (rc[1].empty() || rc[0].size() < rc[1].size()))
  676. return std::move(rc[0]);
  677. else if(!rc[1].empty())
  678. return std::move(rc[1]);
  679. #endif
  680. std::vector<int> ret;
  681. int size=v.size();
  682. std::vector<double> mat(size+1,-1);
  683. std::vector<double> trace(size+1,-1);
  684. std::vector<bool> val(size+2,false);
  685. mat[l[t][0]]=to.dist(v[l[t][0]]);
  686. mat[l[t][1]]=to.dist(v[l[t][1]]);
  687. int f0=l[f][0],f1=l[f][1];
  688. for(int i=0;i<2;i++)
  689. {
  690. if(mat[f0]!=-1 && mat[f1]!=-1)
  691. break;
  692. for(int j=0;j<size;j++)
  693. if(mat[j]!=-1)val[j]=true;
  694. for(int j=0;j<size;j++)
  695. {
  696. if(val[j]==false)continue;
  697. for(unsigned int k=0;k<d[j].size();k++)
  698. {
  699. double dist=v[j].dist(v[d[j][k]]);
  700. if(mat[d[j][k]]==-1 || mat[j]+dist < mat[d[j][k]])
  701. {
  702. mat[d[j][k]] = mat[j]+dist;
  703. trace[d[j][k]] = j;
  704. }
  705. }
  706. }
  707. }
  708. mat[f0]=mat[f0]+from.dist(v[l[f][0]]);
  709. mat[f1]=mat[f1]+from.dist(v[l[f][1]]);
  710. std::vector<point> rc;
  711. if(mat[f0]!=-1 && (mat[f1]==-1 || mat[f0] < mat[f1]))
  712. {
  713. int temp=f0;
  714. while(temp!=-1)
  715. {
  716. rc.push_back(v[temp]);
  717. temp=trace[temp];
  718. }
  719. return std::move(rc);
  720. }
  721. else if(mat[f1]!=-1)
  722. {
  723. int temp=f1;
  724. while(temp!=-1)
  725. {
  726. rc.push_back(v[temp]);
  727. temp=trace[temp];
  728. }
  729. return std::move(rc);
  730. }
  731. return {};
  732. }
  733. };
  734. safe_shared_ptr<graph> g_graph(std::make_shared<graph>());
  735. }//namespace
  736. void card_path::init()
  737. {
  738. std::shared_ptr<graph> local_graph=std::make_shared<graph>();
  739. handle_path hp;
  740. sit_list::instance()->accept(hp);
  741. std::vector<base_path> opath=init_path(hp.ret,hp.v);
  742. local_graph->init(hp.v,opath);
  743. g_graph.set(local_graph);
  744. }
  745. card_path&card_path::inst()
  746. {
  747. static card_path path;
  748. return path;
  749. }
  750. std::vector<point> card_path::find_path(const point&from,const point&to)const
  751. {
  752. return g_graph.get()->find2(from,to);
  753. }
  754. bool card_path::is_at_path(const point&pt)const
  755. {
  756. return g_graph.get()->is_at_path(pt);
  757. }
  758. std::vector<line_v> card_path::find_possible_path(const point&from,double dist) const
  759. {
  760. return std::move(g_graph.get()->find_possible_path(from,dist));
  761. }
  762. #ifdef __DEBUG__
  763. void test_at_path(card_path&cp,const point&pt)
  764. {
  765. if(cp.is_at_path(pt))
  766. log_info("test (%.3lf,%.3lf) is-at-path:true\n",pt.x,pt.y);
  767. else
  768. log_info("test (%.3lf,%.3lf) is-at-path:false\n",pt.x,pt.y);
  769. }
  770. void test_find_path(card_path&cp,const point&p1,const point&p2)
  771. {
  772. printf("\nfind-path: from=(%.3lf,%.3lf),to=(%.3lf,%.3lf)\n",p1.x,p1.y,p2.x,p2.y);
  773. std::vector<point> rc=cp.find_path(p1,p2);
  774. for(uint32_t i=0;i<rc.size();i++)
  775. log_info("x=%.3lf,y=%.3lf\n",rc[i].x,rc[i].y);
  776. }
  777. void test_find_poss_path(const card_path&cp ,const point&from)
  778. {
  779. log_info("\nfind-poss_path: from=(%.3lf,%.3lf)\n",from.x,from.y);
  780. std::vector<line_v> rc=cp.find_possible_path(from,3);
  781. for(uint32_t i=0;i<rc.size();i++)
  782. {
  783. log_info("poss path from=(%.3lf,%.3lf) to=(%.3lf,%.3lf)\n", rc[i][0].x,rc[i][0].y, rc[i][1].x,rc[i][1].y);
  784. }
  785. }
  786. int main()
  787. {
  788. // std::unique_ptr<sit_list> sites(new sit_list());
  789. //sit_list::instance()->load("data_reader_antenna.txt","path_tof.txt");
  790. sit_list::instance()->load("1.txt","2.txt");
  791. card_path cp;
  792. cp.init();
  793. #if 0
  794. {
  795. test_at_path(cp,point(4773.104654,-104.0887));
  796. test_at_path(cp,point(4727,-74.8));
  797. test_at_path(cp,point(4727,-75.0));
  798. test_at_path(cp,point(4727,-75.2));
  799. test_at_path(cp,point(4727,-75.8));
  800. test_at_path(cp,point(4727,-90));
  801. test_at_path(cp,point(4727,-89.6));
  802. test_at_path(cp,point(4727,-89.8));
  803. test_at_path(cp,point(4727,-90));
  804. test_at_path(cp,point(4727,-90.2));
  805. test_at_path(cp,point(4727,-90.4));
  806. }
  807. #endif
  808. //test_at_path(cp,point(4726.90,376.85));
  809. test_find_path(cp,point(-227.6,174.9),point(-201.3,175.5));
  810. test_find_path(cp,point(-227.625219,174.945670),point(-170.085722,176.101574));
  811. test_find_path(cp,point(-393.1944,262.5324),point(-366.0754,274.1253));
  812. //test_find_path(cp,point(4637.000000,-75),point(4727,135));
  813. #if 1
  814. {
  815. test_find_path(cp,point(4637.000000,-75),point(4727,135));
  816. test_find_path(cp,point(4637.000000,-75),point(4727,120));
  817. test_find_path(cp,point(4700,-75),point(4727,120));
  818. test_find_path(cp,point(4725,-75),point(4727,135));
  819. test_find_path(cp,point(4727,-89.7),point(6144.3,-523));
  820. }
  821. #endif
  822. #if 0
  823. {
  824. test_find_poss_path(cp, point(4727,-89));
  825. test_find_poss_path(cp, point(4727,-90));
  826. test_find_poss_path(cp, point(4724,-75));
  827. test_find_poss_path(cp, point(4725,-75));
  828. test_find_poss_path(cp, point(4726,-75));
  829. test_find_poss_path(cp, point(4727,-75));
  830. test_find_poss_path(cp, point(4728,-75));
  831. test_find_poss_path(cp, point(4727,-7));
  832. test_find_poss_path(cp, point(4726.6,33));
  833. }
  834. #endif
  835. return 0;
  836. }
  837. #endif