trm_drivingface_module.cpp 24 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721
  1. #include "trm_drivingface_module.h"
  2. #include "log.h"
  3. #include "three_rates_impl.h"
  4. #include "common_data.h"
  5. #include <string>
  6. std::shared_ptr<drivingface_card> trm_drivingface_module::get_drivingfase_card(std::string card_id)
  7. {
  8. MAP_DRIVINGFACE_CARD::iterator it = mp_drivingface_card_list.find(card_id);
  9. if (it == mp_drivingface_card_list.end())
  10. {
  11. return nullptr;
  12. }
  13. return it->second;
  14. }
  15. std::shared_ptr<drivingface_card> trm_drivingface_module::get_drivingfase_card(uint64_t drivingface_id)
  16. {
  17. for (auto it : mp_drivingface_card_list)
  18. {
  19. if (nullptr != it.second && it.second->m_drivingface_id == drivingface_id)
  20. {
  21. return it.second;
  22. }
  23. }
  24. return nullptr;
  25. }
  26. //移除掘进面
  27. void trm_drivingface_module::remove_drivingface(int drivingface_id )
  28. {
  29. for (MAP_DRIVINGFACE_CARD::iterator it = mp_drivingface_card_list.begin() ; it != mp_drivingface_card_list.end() ;++it)
  30. {
  31. if (nullptr != it->second && (int)it->second->m_drivingface_id == drivingface_id)
  32. {
  33. mp_drivingface_card_list.erase(it);
  34. logn_info(2,"remove_drivingface:%d ",drivingface_id);
  35. break;
  36. }
  37. }
  38. mp_simulate_reader_list.erase(drivingface_id);
  39. }
  40. int trm_drivingface_module::init_all(bool status)
  41. {
  42. set_restart(status);
  43. init_reader();
  44. init_drivingface_card();
  45. init_drivingface_ref_points();
  46. return 0;
  47. }
  48. int trm_drivingface_module::init_reader()
  49. {
  50. const char* sql = "select reader_id from dat_reader where enable_simulate_card=1;";
  51. std::string error = "";
  52. MYSQL_RES* pRes = nullptr;
  53. MYSQL_ROW row;
  54. pRes = sDBConnPool.Query(sql,error);
  55. if(nullptr == pRes){
  56. logn_error(2,"init_reader Query exist error, error: %s", error.c_str());
  57. return -1;
  58. }
  59. std::shared_ptr<reader_info> reader_ptr = nullptr;
  60. while(NULL != (row = mysql_fetch_row(pRes))){
  61. uint32_t reader_id = atoi(row[0]==NULL?0:row[0]);
  62. auto it = mp_simulate_reader_list.find(reader_id);
  63. if(it!=mp_simulate_reader_list.end()){
  64. reader_ptr = it->second;
  65. }else{
  66. reader_ptr = std::make_shared<reader_info>();
  67. mp_simulate_reader_list.insert({reader_id,reader_ptr});
  68. }
  69. reader_ptr->m_reader_id = reader_id;
  70. }
  71. mysql_free_result(pRes);
  72. return 0;
  73. }
  74. /*
  75. * 初始化掘进机卡信息
  76. *
  77. * 参数
  78. * 无
  79. *
  80. * 返回值
  81. * 返回查询记录条数
  82. *
  83. */
  84. int trm_drivingface_module::init_drivingface_card(const std::string & sz_drivingface_id/* = "-1"*/)
  85. {
  86. std::string sql = "select c.card_id, b.base_point_x, b.base_point_y, b.base_point_z, b.drivingface_id, d.area_id, a.warning_threshold, \
  87. a.over_count_num, d.map_id, b.drivingface_type, a.small_reader_id, a.big_reader_id, a.schedule_work_time, \
  88. a.schedule_tunnelling_times, b.drifting_footage_unit, c.dept_id, a.vehicle_id, a.relay_small_reader_id \
  89. from dat_drivingface_vehicle a, dat_drivingface b, dat_vehicle_extend c ,dat_work_face d\
  90. where a.vehicle_id = c.vehicle_id and a.drivingface_id = b.drivingface_id and a.drivingface_id = d.work_face_id";
  91. if (std::atoi(sz_drivingface_id.c_str()) > 0 )
  92. {
  93. sql += " and a.drivingface_id = " + sz_drivingface_id ;
  94. }
  95. sql.append(";");
  96. std::string error;
  97. YADB::CDBResultSet dbRes;
  98. sDBConnPool.Query(sql.c_str(),dbRes,error);
  99. int nCount = dbRes.GetRecordCount(error);
  100. if(nCount > 0){
  101. while(dbRes.GetNextRecod(error)){
  102. std::string card_id = "";
  103. dbRes.GetField("card_id",card_id,error);
  104. double bpx = 0.0;
  105. dbRes.GetField("base_point_x",bpx,error);
  106. double bpy = 0.0;
  107. dbRes.GetField("base_point_y",bpy,error);
  108. double bpz = 0.0;
  109. dbRes.GetField("base_point_z",bpz,error);
  110. int id = 0;
  111. dbRes.GetField("drivingface_id",id,error);
  112. int area_id = 0;
  113. dbRes.GetField("area_id",area_id,error);
  114. double wth = 0.0;
  115. dbRes.GetField("warning_threshold",wth,error);
  116. int ocn = 0;
  117. dbRes.GetField("over_count_num",ocn,error);
  118. int map_id = 0;
  119. dbRes.GetField("map_id",map_id,error);
  120. int dt = 0;
  121. dbRes.GetField("drivingface_type",dt,error);
  122. int sri = 0;
  123. dbRes.GetField("small_reader_id",sri,error);
  124. int bri = 0;
  125. dbRes.GetField("big_reader_id",bri,error);
  126. int swt = 0;
  127. dbRes.GetField("schedule_work_time",swt,error);
  128. double stt = 0.0;
  129. dbRes.GetField("schedule_tunnelling_times",stt,error);
  130. double dfu = 0.0;
  131. dbRes.GetField("drifting_footage_unit",dfu,error);
  132. int dept_id = 0;
  133. dbRes.GetField("dept_id",dept_id,error);
  134. int v_id = 0;
  135. dbRes.GetField("vehicle_id",v_id,error);
  136. int rsr = 0;
  137. dbRes.GetField("relay_small_reader_id",rsr,error);
  138. std::shared_ptr<drivingface_card> pdc = get_drivingfase_card(id);
  139. if(nullptr == pdc)
  140. {
  141. pdc = std::make_shared<drivingface_card>();
  142. mp_drivingface_card_list.insert({card_id,pdc});
  143. }
  144. pdc->m_card_id = card_id;
  145. pdc->m_drivingface_id = id;
  146. pdc->m_vehicle_id = v_id;
  147. pdc->m_area_id = area_id;
  148. pdc->m_relay_small_reader_id = rsr;
  149. pdc->m_locate_small_reader_id = sri;
  150. pdc->m_big_reader_id = bri;
  151. pdc->m_dept_id = dept_id;
  152. pdc->m_schedule_tunnelling_times = stt;
  153. pdc->m_schedule_work_times = swt;
  154. pdc->m_drifting_footage_unit = dfu;
  155. pdc->x = bpx;
  156. pdc->y = bpy;
  157. pdc->z = bpz;
  158. }
  159. }
  160. logn_info(2,"Init drivingface:%s Count=%d",sz_drivingface_id.c_str(),nCount);
  161. return nCount;
  162. }
  163. /*
  164. * 初始化掘进机-掘进面偏移数据
  165. *
  166. * 参数
  167. * 无
  168. *
  169. * 返回值
  170. * 返回查询记录条数
  171. *
  172. */
  173. int trm_drivingface_module::init_drivingface_ref_points(const std::string & sz_drivingface_id/* = "-1"*/)
  174. {
  175. std::string sql = "select drivingface_id,idx,base_x,base_y,base_z,offset from dat_drivingface_ref_point";
  176. if (std::atoi(sz_drivingface_id.c_str()) > 0 )
  177. {
  178. sql += " where drivingface_id = " + sz_drivingface_id ;
  179. }
  180. sql += " order by drivingface_id asc,idx asc;";
  181. std::string error;
  182. YADB::CDBResultSet dbRes;
  183. sDBConnPool.Query(sql.c_str(),dbRes,error);
  184. int nCount = dbRes.GetRecordCount(error);
  185. if(nCount > 0)
  186. {
  187. struct sref_point
  188. {
  189. std::vector<point> po_list;
  190. double fOffset;
  191. };
  192. std::map<int,sref_point> map_points ;
  193. while(dbRes.GetNextRecod(error))
  194. {
  195. int v_idx = 0;
  196. dbRes.GetField("idx",v_idx,error);
  197. int driv_id = 0;
  198. dbRes.GetField("drivingface_id",driv_id,error);
  199. int db_offset = 0;
  200. dbRes.GetField("offset",db_offset,error);
  201. double x = 0;
  202. dbRes.GetField("base_x", x, error);
  203. double y = 0;
  204. dbRes.GetField("base_y", y, error);
  205. double z = 0;
  206. dbRes.GetField("base_z", z, error);
  207. point po(x,y,z);
  208. auto it = map_points.find(driv_id);
  209. if (it == map_points.end())
  210. {
  211. sref_point v ;
  212. v.po_list.push_back(po);
  213. v.fOffset = db_offset;
  214. map_points[driv_id] = v;
  215. continue;
  216. }
  217. sref_point & t_ref = map_points[driv_id];
  218. if ( v_idx > (int)t_ref.po_list.size())
  219. {
  220. t_ref.po_list.push_back(po);
  221. t_ref.fOffset = db_offset;
  222. }
  223. }
  224. for (auto &it : map_points)
  225. {
  226. std::shared_ptr<drivingface_card> drivingface_ptr = get_drivingfase_card((uint64_t)it.first);
  227. if (nullptr != drivingface_ptr)
  228. {
  229. drivingface_ptr->m_vt_ref_points = it.second.po_list;
  230. drivingface_ptr->m_fOffset = it.second.fOffset;
  231. }
  232. }
  233. }
  234. logn_info(2,"init_drivingface_ref_points: drivingface=%s sql=%s",sz_drivingface_id.c_str(),sql.c_str());
  235. return nCount;
  236. }
  237. /*
  238. * 如果采集重启了,需要从数据库中查找最新的最大掘进距离及坐标信息
  239. *
  240. * 参数
  241. * pCard 卡信息
  242. * 返回值
  243. * 正常返回0,否则返回其他值
  244. *
  245. * */
  246. int trm_drivingface_module::init_drivingface_nearest_info(std::shared_ptr<drivingface_card> pCard)
  247. {
  248. //如果采集重启了,需要从数据库中加载历史最大掘进距离及坐标信息
  249. if(nullptr != pCard && pCard->m_restart)
  250. {
  251. char sql[2000] = {0};
  252. snprintf(sql,sizeof(sql),
  253. "select start_x,start_y from his_regular_cycle_detail where start_time=(select max(start_time) \
  254. from his_regular_cycle_detail where work_face_id =%d) and work_face_id =%d;",
  255. (int)pCard->m_drivingface_id,
  256. (int)pCard->m_drivingface_id
  257. );
  258. std::string error = "";
  259. MYSQL_ROW row;
  260. MYSQL_RES* pRes = nullptr;
  261. pRes = sDBConnPool.Query(sql,error);
  262. if(nullptr == pRes){
  263. logn_error(2,"init_drivingface_nearest_info Query exist error, error: %s", error.c_str());
  264. return -1;
  265. }
  266. while(NULL != (row = mysql_fetch_row(pRes))){
  267. double x = row[0]==NULL?0:atof(row[0]);
  268. double y = row[1]==NULL?0:atof(row[1]);
  269. pCard->m_max_point.set(x,y);
  270. }
  271. mysql_free_result(pRes);
  272. //保存基准点的坐标
  273. double map_scale = G_CommonData->m_map_scale;
  274. point p(pCard->x,pCard->y);
  275. int idx = pCard->m_vt_ref_points.size();
  276. if (idx > 0 )
  277. {
  278. p.set(pCard->m_vt_ref_points[idx - 1]);
  279. if (idx > 1 && pCard->m_total_ref_point_dist < ZERO_PRECISION )
  280. {
  281. double d = 0.0;
  282. point tp(pCard->m_vt_ref_points[0]);
  283. for (int i = 1; i <= idx ; ++i)
  284. {
  285. point ttp(pCard->m_vt_ref_points[i]);
  286. d += tp.dist(ttp) * map_scale;
  287. }
  288. pCard->m_total_ref_point_dist = d;
  289. logn_info(2,"[init_drivingface_recently_info] drivingface_id: %d, trpd: %.4f",pCard->m_drivingface_id,pCard->m_total_ref_point_dist);
  290. }
  291. }
  292. //如果数据库中无最大距离和位置数据,则根据当前卡计算并保存
  293. //如果有数据,则保存最大距离信息
  294. if(pCard->m_max_point.empty())
  295. {
  296. pCard->m_max_point.set(pCard->x, pCard->y);
  297. }
  298. pCard->m_max_distance = pCard->m_total_ref_point_dist + pCard->m_max_point.dist(p) * map_scale + pCard->m_fOffset;
  299. pCard->m_restart = false;
  300. }
  301. return -1;
  302. }
  303. int trm_drivingface_module::deal_drivingface_service(std::shared_ptr<drivingface_card> pCard,std::shared_ptr<card_pos> p_tcp_card)
  304. {
  305. if(nullptr == pCard || nullptr == p_tcp_card)
  306. {
  307. return -1;
  308. }
  309. //更新机器信息
  310. pCard->x = p_tcp_card->x;
  311. pCard->y = p_tcp_card->y;
  312. pCard->m_rec_time = p_tcp_card->rec_time;
  313. //确保掘进机已读取最后一次的位置及最大距离
  314. init_drivingface_nearest_info(pCard);
  315. time_t cur_time = time(NULL);
  316. time_point tp;
  317. tp.m_t = cur_time;
  318. tp.x = pCard->x;
  319. tp.y = pCard->y;
  320. if(!tp.empty())
  321. {
  322. pCard->m_vt_points.push_back(tp);
  323. //记录时刻的位置
  324. deal_drivingface_real_distance(pCard,tp);
  325. //保存掘进米数
  326. size_t len = pCard->m_vt_points.size();
  327. if(cur_time - pCard->m_vt_points[0].m_t >= 60 && len > 0)
  328. {
  329. double sum_x = 0.0, sum_y = 0.0;
  330. for(size_t i = 0; i < len;++i)
  331. {
  332. sum_x += pCard->m_vt_points[i].x;
  333. sum_y += pCard->m_vt_points[i].y;
  334. }
  335. deal_drivingface_regular_cycle(pCard,point(sum_x/len,sum_y/len,0));
  336. }
  337. }
  338. return 0;
  339. }
  340. /*
  341. * 正常正规循环率处理逻辑
  342. * */
  343. int trm_drivingface_module::deal_drivingface_regular_cycle(std::shared_ptr<drivingface_card> pCard, const point& p)
  344. {
  345. save_drivingface_regular_cycle(pCard,p);
  346. return 0;
  347. }
  348. /*
  349. * 超时正规循环率处理逻辑
  350. * */
  351. int trm_drivingface_module::deal_drivingface_regular_cycle()
  352. {
  353. time_t cur_time = time(NULL);
  354. std::string day_end_time = "";
  355. day_end_time = tools::time_tools::time_t2string(cur_time);
  356. day_end_time = day_end_time.substr(11);
  357. for(auto it : mp_drivingface_card_list)
  358. {
  359. int len = (int)it.second->m_vt_points.size();
  360. if(len > 0)
  361. {
  362. if(cur_time - it.second->m_vt_points[len-1].m_t > 120 || day_end_time=="23:59:59")
  363. {
  364. double sum_x = 0.0, sum_y = 0.0;
  365. for(int i = 0;i < len ; ++i)
  366. {
  367. sum_x += it.second->m_vt_points[i].x;
  368. sum_y += it.second->m_vt_points[i].y;
  369. }
  370. if("23:59:59" == day_end_time){
  371. logn_info(2,"deal_drivingface_regular_cycle deal cross-day problem");
  372. }
  373. save_drivingface_regular_cycle(it.second,point(sum_x / len,sum_y / len));
  374. }
  375. }
  376. }
  377. return 0;
  378. }
  379. /*
  380. * 正常坐标同步处理:保存1分钟的掘进距离和时间信息到his_draw_position表内,用于web端画实时掘进曲线图使用
  381. *
  382. * 参数
  383. * pCard :掘进机卡
  384. * p :坐标
  385. * 返回值
  386. * 正常返回0,否则返回其他值
  387. *
  388. * */
  389. int trm_drivingface_module::deal_drivingface_real_distance(std::shared_ptr<drivingface_card> pCard,const point& p)
  390. {
  391. char meta_sql[100] = {'\0'};
  392. double cur_distance = 0.0;
  393. double map_scale = G_CommonData->m_map_scale;
  394. int idx = pCard->m_vt_ref_points.size()-1;
  395. if (idx < 0)
  396. {
  397. logn_error(2,"[deal_drivingface_real_distance] drivingface_id: %d no ref point info.",pCard->m_drivingface_id);
  398. return -1;
  399. }
  400. point base_point;
  401. base_point.set(pCard->m_vt_ref_points[idx]);
  402. cur_distance = pCard->m_total_ref_point_dist + p.dist(base_point) * map_scale + pCard->m_fOffset;
  403. logn_info(2,"[deal_drivingface_real_distance] card_id: %s, cur_distance: %.3f, offset: %.3f, x: %.3f, y: %.3f, drivingface_id: %d, ref_totals: %d, ref_idx: %d, ref_x: %.3f, ref_y: %.3f",
  404. pCard->m_card_id.c_str(),cur_distance,pCard->m_fOffset,
  405. pCard->x,pCard->y,
  406. pCard->m_drivingface_id,pCard->m_vt_ref_points.size(),
  407. idx,pCard->m_vt_ref_points[idx].x,pCard->m_vt_ref_points[idx].y
  408. );
  409. time_t cur_time = time(NULL);
  410. if (pCard->m_b_first_record)
  411. {
  412. pCard->m_b_first_record = false;
  413. pCard->m_str_record = "";
  414. pCard->m_record_cycle_start_time = cur_time;
  415. pCard->m_record_avg_dist += cur_distance;
  416. pCard->m_record_max_dist = pCard->m_record_min_dist = cur_distance;
  417. pCard->m_record_totals++;
  418. snprintf(meta_sql,sizeof(meta_sql),"%s,%.4f;",tools::time_tools::time_t2string(cur_time).c_str(),cur_distance);
  419. pCard->m_str_record = meta_sql;
  420. }
  421. else
  422. {
  423. snprintf(meta_sql,sizeof(meta_sql),"%s,%.4f;",tools::time_tools::time_t2string(cur_time).c_str(),cur_distance);
  424. std::string r = meta_sql;
  425. pCard->m_str_record += r;
  426. pCard->m_record_avg_dist += cur_distance;
  427. pCard->m_record_totals++;
  428. pCard->m_record_max_dist = pCard->m_record_max_dist > cur_distance ? pCard->m_record_max_dist : cur_distance;
  429. pCard->m_record_min_dist = pCard->m_record_min_dist < cur_distance ? pCard->m_record_min_dist : cur_distance;
  430. //如果有一分钟的数据,则保存结果
  431. if (cur_time - pCard->m_record_cycle_start_time >= 60)
  432. {
  433. if (pCard->m_record_totals>0)
  434. {
  435. pCard->m_record_avg_dist /= pCard->m_record_totals;
  436. }
  437. char t_sql_log[8192];
  438. memset(t_sql_log,0,8192*sizeof(char));
  439. sprintf(t_sql_log,"insert ignore into his_draw_position(work_face_id,write_time,avg_distance,max_distance,min_distance) values('%d','%s',%.4f,%.4f,%.4f);",
  440. (int)pCard->m_drivingface_id,
  441. tools::time_tools::time_t2string(cur_time).c_str(),
  442. pCard->m_record_avg_dist,
  443. pCard->m_record_max_dist,
  444. pCard->m_record_min_dist);
  445. std::string error = "";
  446. if (sDBConnPool.ExecuteSql(t_sql_log,error ) < 0 )
  447. {
  448. logn_error(2,"deal_drivingface_real_distance Failed to ExecuteSql:%s,Err=%s\n", t_sql_log, error.c_str());
  449. }
  450. pCard->m_str_record = "";
  451. pCard->m_record_cycle_start_time = cur_time;
  452. pCard->m_record_avg_dist = pCard->m_record_max_dist = 0.0;
  453. pCard->m_record_min_dist = 999999.9;
  454. pCard->m_record_totals = 0;
  455. }
  456. }
  457. return 0;
  458. }
  459. /*
  460. * 超时检查处理:保存1分钟的掘进距离和时间信息到his_draw_position表内,用于web端画实时掘进曲线图使用
  461. *
  462. * 参数
  463. * 无
  464. * 返回值
  465. * 正常返回0,否则返回其他值
  466. *
  467. * */
  468. int trm_drivingface_module::deal_drivingface_real_distance()
  469. {
  470. for(auto it : mp_drivingface_card_list)
  471. {
  472. time_t cur_time = time(NULL);
  473. std::shared_ptr<drivingface_card> card = it.second;
  474. //b.当前时间大于开始记录的起始时间2分钟;
  475. //c.卡的记录的内容长度大于0
  476. if(cur_time - it.second->m_record_cycle_start_time >= 120 && it.second->m_str_record.length() > 0)
  477. {
  478. //计算平均距离
  479. if (it.second->m_record_totals > 0)
  480. {
  481. it.second->m_record_avg_dist /= it.second->m_record_totals;
  482. }
  483. if (it.second->m_record_max_dist < 1E-4 && it.second->m_record_max_dist < it.second->m_record_avg_dist)
  484. {
  485. it.second->m_record_max_dist = it.second->m_record_avg_dist;
  486. }
  487. if (it.second->m_record_min_dist >= 999999.9 && it.second->m_record_min_dist > it.second->m_record_avg_dist)
  488. {
  489. it.second->m_record_min_dist = it.second->m_record_avg_dist;
  490. }
  491. char sql[8192] = {'\0'};
  492. sprintf(sql,"insert ignore into his_draw_position(work_face_id,write_time,avg_distance,max_distance,min_distance) values('%d','%s',%.4f,%.4f,%.4f);",
  493. (int)it.second->m_drivingface_id,
  494. tools::time_tools::time_t2string(cur_time).c_str(),
  495. it.second->m_record_avg_dist,
  496. it.second->m_record_max_dist,
  497. it.second->m_record_min_dist);
  498. std::string log = "";
  499. std::string error = "";
  500. if(sDBConnPool.ExecuteSql(sql,error) < 0){
  501. logn_error(2,"deal_drivingface_real_distance null param Failed to ExecuteSql:%s,Err=%s\n", sql, error.c_str());
  502. }
  503. it.second->m_str_record = "";
  504. it.second->m_record_cycle_start_time = 0;
  505. it.second->m_b_first_record = true;
  506. it.second->m_record_avg_dist = it.second->m_record_max_dist = 0.0;
  507. it.second->m_record_min_dist = 999999.9;
  508. it.second->m_record_totals = 0;
  509. }
  510. }
  511. return 0;
  512. }
  513. /*
  514. * 将掘进机的最大掘进距离和坐标保存到数据库中
  515. *
  516. * 参数
  517. * pCard 掘进机信息
  518. * p 当前传入的卡定位坐标
  519. *
  520. * 返回值
  521. * 正常返回0,否则返回其他值
  522. * */
  523. int trm_drivingface_module::save_drivingface_regular_cycle(std::shared_ptr<drivingface_card> pCard,const point& p)
  524. {
  525. if(pCard->m_drifting_footage_unit < 1E-4){
  526. logn_error(2,"save_drivingface_regular_cycle: drivingface:%d-%s input params(drifting_footage_unit) is illegal"
  527. ,pCard->m_drivingface_id,pCard->m_card_id.c_str());
  528. return -1;
  529. }
  530. //处理时间
  531. time_t cur_time = time(NULL);
  532. std::string start_time = tools::time_tools::time_t2string(pCard->m_vt_points[0].m_t);
  533. std::string end_time = tools::time_tools::time_t2string(cur_time);
  534. //计算本次定位点p与基准点的距离
  535. int idx = pCard->m_vt_ref_points.size()-1;
  536. if (idx < 0)
  537. {
  538. logn_error(2,"[regular_cycle] drivingface_id: %d no ref point info.\n",pCard->m_drivingface_id);
  539. return -1;
  540. }
  541. point base_point(pCard->m_vt_ref_points[idx]);
  542. double cur_distance = 0.0;
  543. cur_distance = pCard->m_total_ref_point_dist + p.dist(base_point) * G_CommonData->m_map_scale + pCard->m_fOffset;
  544. logn_info(2,"[regular_cycle] card_id: %s, drivingface_id: %d, cur_distance: %.4f, max_distance: %.4f, distanceToRef: %.4f, offset: %.4f, totalRefdist: %.4f, x: %.4f ,y: %.4f"
  545. ,pCard->m_card_id.c_str(), pCard->m_drivingface_id,cur_distance,pCard->m_max_distance,p.dist(base_point)* G_CommonData->m_map_scale
  546. ,pCard->m_fOffset,pCard->m_total_ref_point_dist,p.x, p.y);
  547. //计算本次定位点与基准点的距离
  548. if(cur_distance > pCard->m_max_distance)
  549. {
  550. //计算排数
  551. double row_space = 0.0;
  552. row_space = (cur_distance - pCard->m_max_distance);
  553. //计算排数信息
  554. double schedule_value = 0.0;
  555. schedule_value = get_drivingface_schedule_value(pCard->m_drivingface_id,2);
  556. double sv = schedule_value*pCard->m_drifting_footage_unit;
  557. if (abs(sv) < 1E-4)
  558. {
  559. sv = 8.0;
  560. }
  561. if (row_space > sv*1.5)
  562. {
  563. smooth_row_spacing(row_space,sv);
  564. }
  565. double row_spacing = row_space;
  566. //保存最大进尺和对应的坐标
  567. pCard->m_max_distance = cur_distance;
  568. pCard->m_max_point.set(p);
  569. //数据入库
  570. char sql[500] = {'\0'};
  571. snprintf(sql,
  572. sizeof(sql),
  573. "insert ignore into his_regular_cycle_detail(work_face_id,detail_type,start_time,end_time,detail_value,schedule_value,dept_id,start_x,start_y) values(%d,%d,'%s','%s',%.4f,%.4f,%d,%.3f,%.3f);",
  574. (int)pCard->m_drivingface_id,
  575. 2,
  576. start_time.c_str(),
  577. end_time.c_str(),
  578. row_spacing,
  579. schedule_value,
  580. (int)pCard->m_dept_id,
  581. p.x,p.y);
  582. std::string error = "";
  583. if(sDBConnPool.ExecuteSql(sql,error) < 0){
  584. logn_error(2,"save_drivingface_regular_cycle Failed to ExecuteSql:%s,Err=%s\n", sql, error.c_str());
  585. }
  586. }
  587. pCard->m_vt_points.resize(0);
  588. return 0;
  589. }
  590. /*
  591. * 平滑掘进机进尺的距离信息
  592. *
  593. * param
  594. * value 需要平滑的进尺距离
  595. * sv 掘进面计划进尺
  596. *
  597. */
  598. void trm_drivingface_module::smooth_row_spacing(double& value,const double& sv)
  599. {
  600. //debug_print_syslog(0,"[smooth_row_spacing] before smooth: value: %.4f , standard_value: %.4f",value,sv);
  601. int m = (int)value/((int)sv);
  602. double tmp_value = 0.0;
  603. tmp_value = value - m*sv;
  604. time_t s = time(NULL);
  605. struct tm * p = localtime(&s);
  606. if (p->tm_hour <= 12)
  607. {
  608. tmp_value = tmp_value/2;
  609. }
  610. //debug_print_syslog(0,"[smooth_row_spacing] after smooth: value: %.4f , standard_value: %.4f",tmp_value,sv);
  611. value = tmp_value;
  612. }
  613. double trm_drivingface_module::get_drivingface_schedule_value(const uint64_t& id,const uint8_t type)
  614. {
  615. double ret = 0.0;
  616. char sql[500] = {'\0'};
  617. std::string cur_time = tools::time_tools::time_t2string(time(NULL));
  618. snprintf(sql,sizeof(sql),"select workface_id,schedule_tunnelling_times from dat_workface_scheduling where schedule_date=date('%s') and workface_id=%d;",
  619. cur_time.c_str(),
  620. (int)id);
  621. MYSQL_RES* pRes = nullptr;
  622. MYSQL_ROW row;
  623. std::string error = "";
  624. pRes = sDBConnPool.Query(sql,error);
  625. if(nullptr == pRes){
  626. logn_error(2,"get_drivingface_schedule_value Query exist error, error: %s", error.c_str());
  627. return ret;
  628. }
  629. //uint64_t face_id = 0;
  630. while(NULL != (row = mysql_fetch_row(pRes))){
  631. //face_id = atoi(row[0] == NULL?0:row[0]);
  632. ret = atof(row[1]==NULL?0:row[1]);
  633. }
  634. mysql_free_result(pRes);
  635. return ret;
  636. }