조성현

중간저장

...@@ -53,4 +53,5 @@ void EdgeItem::paint(QPainter * painter, const QStyleOptionGraphicsItem * option ...@@ -53,4 +53,5 @@ void EdgeItem::paint(QPainter * painter, const QStyleOptionGraphicsItem * option
53 pen.setColor(color); 53 pen.setColor(color);
54 painter->setPen(pen); 54 painter->setPen(pen);
55 painter->drawLine(QLineF(x1, y1, x2, y2)); 55 painter->drawLine(QLineF(x1, y1, x2, y2));
56 + //painter->drawText(QPoint((x1 + x2) / 2, (y1 + y2) / 2), "hi");
56 } 57 }
......
...@@ -444,21 +444,6 @@ void GraphItem::might_know() ...@@ -444,21 +444,6 @@ void GraphItem::might_know()
444 } 444 }
445 } 445 }
446 446
447 -void GraphItem::reset_color()
448 -{
449 - for (auto& n: nodeList) {
450 - if (n->getType() == NODE_PAPER) {
451 - n->setColor(QColor(Qt::darkGreen));
452 - } else {
453 - n->setColor(QColor(Qt::green));
454 - }
455 - }
456 - for (auto& e: edgeList) {
457 - e->setColor(Qt::black);
458 - e->setWidth(0);
459 - }
460 -}
461 -
462 void GraphItem::topK_highlight_with_total() 447 void GraphItem::topK_highlight_with_total()
463 { 448 {
464 // 전체 그래프 기준 topK highlight 449 // 전체 그래프 기준 topK highlight
...@@ -479,9 +464,22 @@ void GraphItem::topK_highlight_with_total() ...@@ -479,9 +464,22 @@ void GraphItem::topK_highlight_with_total()
479 // boost::put(vertex_record, *graph, *vi, 0); 464 // boost::put(vertex_record, *graph, *vi, 0);
480 //} 465 //}
481 466
482 - // <record, label> 467 + //k 입력
483 - //저자별 논문 수 계산 468 + bool isok = false;
484 - TopKHeap<pair<int, string>> heap(TOP_K); 469 +
470 + QInputDialog *inputDialog = new QInputDialog();
471 + //int inputK = inputDialog->getText(nullptr, "Enter target's name", "Start node's name:",
472 + // QLineEdit::Normal, "Akira Idoue", &isok).toStdString();
473 + int inputK = inputDialog->getInt(nullptr, "Enter K", "K:", 3,
474 + 1, whole_node_cnt, 1, &isok);
475 + if (!isok) {
476 + qDebug("input cancelled");
477 + return;
478 + }
479 +
480 + //저자별 논문 수 계산 + TopK Heap 사용
481 + //pair -> <num_of_record, label>
482 + TopKHeap<pair<int, string>> heap(inputK);
485 for (boost::tie(vi, vi_end) = boost::vertices(*graph); vi != vi_end; ++vi) { 483 for (boost::tie(vi, vi_end) = boost::vertices(*graph); vi != vi_end; ++vi) {
486 if (node_type_map[*vi] != NODE_TYPE::NODE_AUTHOR) { 484 if (node_type_map[*vi] != NODE_TYPE::NODE_AUTHOR) {
487 continue; 485 continue;
...@@ -502,8 +500,9 @@ void GraphItem::topK_highlight_with_total() ...@@ -502,8 +500,9 @@ void GraphItem::topK_highlight_with_total()
502 } 500 }
503 501
504 //get top K records 502 //get top K records
505 - pair<int, string> topk_arr[TOP_K]; 503 + //pair<int, string> topk_arr[inputK];
506 - for (int i = 0; i < TOP_K; ++i) { 504 + pair<int, string> *topk_arr = new pair<int, string>[inputK];
505 + for (int i = 0; i < inputK; ++i) {
507 topk_arr[i] = heap.pop(); 506 topk_arr[i] = heap.pop();
508 qDebug() << "topk["<<i<<"] = " << topk_arr[i].first << ", " << QString::fromStdString(topk_arr[i].second); 507 qDebug() << "topk["<<i<<"] = " << topk_arr[i].first << ", " << QString::fromStdString(topk_arr[i].second);
509 } 508 }
...@@ -512,13 +511,227 @@ void GraphItem::topK_highlight_with_total() ...@@ -512,13 +511,227 @@ void GraphItem::topK_highlight_with_total()
512 for (auto& n: nodeList) { 511 for (auto& n: nodeList) {
513 auto label = n->getLabel(); 512 auto label = n->getLabel();
514 n->setColor(QColor(Qt::lightGray)); 513 n->setColor(QColor(Qt::lightGray));
515 - for (auto& p: topk_arr) { 514 + for (int i = 0; i < inputK; ++i) {
515 + auto& p = topk_arr[i];
516 if (label.toStdString() == p.second) { 516 if (label.toStdString() == p.second) {
517 n->setColor(QColor(Qt::red)); 517 n->setColor(QColor(Qt::red));
518 break; 518 break;
519 } 519 }
520 } 520 }
521 } 521 }
522 + delete[] topk_arr;
523 +}
524 +
525 +void GraphItem::topK_highlight_with_target()
526 +{
527 + // 선택한 사람 주변 topK highlight
528 +
529 + // 저자 노드별 실적 계산
530 + vertex_iterator vi, vi_end;
531 + vertex_descriptor vtarget;
532 + Graph::adjacency_iterator ai, ai_end,
533 + ai2, ai2_end;
534 +
535 + auto node_idx_map = boost::get(vertex_index, *graph);
536 + auto node_label_map = boost::get(vertex_name, *graph);
537 + auto node_type_map = boost::get(vertex_type, *graph);
538 + auto node_records_map = boost::get(vertex_record, *graph);
539 +
540 + vector<vertex_descriptor> paper_vec;
541 + vector<string> visited;
542 +
543 + vector<vertex_descriptor> target_desc_range_vec;
544 +
545 + //k 입력
546 + bool isok = false;
547 +
548 + QInputDialog *inputDialog = new QInputDialog();
549 + //int inputK = inputDialog->getText(nullptr, "Enter target's name", "Start node's name:",
550 + // QLineEdit::Normal, "Akira Idoue", &isok).toStdString();
551 + int inputK = inputDialog->getInt(nullptr, "Enter K", "K:", 3,
552 + 1, whole_node_cnt, 1, &isok);
553 + if (!isok) {
554 + qDebug("input cancelled");
555 + return;
556 + }
557 +
558 + //std::string target_name = inputDialog->getText
559 + std::string target_name = inputDialog->getText(nullptr, "Enter target's name",
560 + "target node's name:", QLineEdit::Normal, "Tobias Scholand", &isok).toStdString();
561 + if (!isok) {
562 + qDebug("input cancelled");
563 + return;
564 + }
565 + qDebug() << target_name.c_str();
566 +
567 +
568 + // find target node
569 + for (boost::tie(vi, vi_end) = boost::vertices(*graph); vi != vi_end; ++vi) {
570 + if (node_label_map[*vi] == target_name) {
571 + target_desc_range_vec.push_back(*vi);
572 + vtarget = vertex(node_idx_map[*vi], *graph);
573 + break;
574 + }
575 + }
576 + visited.push_back(target_name);
577 +
578 + //push target's papers
579 + for (boost::tie(ai, ai_end) = boost::adjacent_vertices(vtarget, *graph);
580 + ai != ai_end;
581 + ++ai) {
582 + //ai: 타겟 노드의 이웃 노드(paper)
583 + const string& node_label = node_label_map[*ai];
584 + paper_vec.push_back(vertex(node_idx_map[*ai], *graph));
585 + visited.push_back(node_label);
586 + }
587 +
588 + // find coauthor
589 + for (auto paper : paper_vec) {
590 + //paper: 타겟 저자의 논문
591 + for (boost::tie(ai, ai_end) = boost::adjacent_vertices(paper, *graph);
592 + ai != ai_end;
593 + ++ai) {
594 +
595 + //ai: paper의 이웃. = 저자들
596 + // == coauthors
597 + const string& node_label = node_label_map[*ai];
598 + if (find(visited.begin(), visited.end(), node_label) != visited.end()) {
599 + continue;
600 + }
601 +
602 + target_desc_range_vec.push_back(vertex(node_idx_map[*ai], *graph));
603 + visited.push_back(node_label);
604 + }
605 + }
606 +
607 +
608 + //저자별 논문 수 계산 + TopK Heap 사용
609 + //target range에 대해 topK 구하기
610 + //pair -> <num_of_record, label>
611 + TopKHeap<pair<int, string>> heap(inputK);
612 + for (auto& n: target_desc_range_vec) {
613 + //if not author --> skip
614 + if (node_type_map[n] != NODE_TYPE::NODE_AUTHOR) {
615 + continue;
616 + }
617 +
618 + const string& node_label = node_label_map[n];
619 + int record_cnt = 0;
620 + //cnt
621 + for (boost::tie(ai, ai_end) = boost::adjacent_vertices(n, *graph);
622 + ai != ai_end;
623 + ++ai) {
624 + ++record_cnt;
625 + }
626 +
627 + boost::put(vertex_record, *graph, n, record_cnt);
628 + heap.push(make_pair(record_cnt, node_label));
629 + }
630 +
631 + //get top K records
632 + int heap_sz = std::min(inputK, heap.getSize());
633 + pair<int, string> *topk_arr = new pair<int, string>[heap_sz];
634 + for (int i = 0; i < heap_sz; ++i) {
635 + topk_arr[i] = heap.pop();
636 + qDebug() << "topk[" << i << "] = " << topk_arr[i].first << ", " << QString::fromStdString(topk_arr[i].second);
637 + }
638 +
639 +
640 + for (auto& n : nodeList) {
641 + auto label = n->getLabel();
642 + if (label.toStdString() != target_name) {
643 + n->setColor(QColor(Qt::lightGray));
644 + }
645 + else {
646 + n->setColor(QColor(Qt::blue));
647 + }
648 +
649 + //in target range
650 + if (find(visited.begin(), visited.end(), label.toStdString()) != visited.end()) {
651 + n->setColor(QColor(Qt::green));
652 + }
653 +
654 + //if topK
655 + for (int i = 0; i < heap_sz; ++i) {
656 + auto& p = topk_arr[i];
657 + if (label.toStdString() == p.second) {
658 + n->setColor(QColor(Qt::red));
659 + break;
660 + }
661 + }
662 + }
663 +
664 + delete[] topk_arr;
665 +}
666 +
667 +void GraphItem::topK_using_custom_score()
668 +{
669 + // 전체 그래프 기준 topK highlight
670 +
671 + // 저자 노드별 실적 계산
672 + vertex_iterator vi, vi_end;
673 + Graph::adjacency_iterator ai, ai_end;
674 +
675 + auto node_label_map = boost::get(vertex_name, *graph);
676 + auto node_type_map = boost::get(vertex_type, *graph);
677 + auto node_records_map = boost::get(vertex_record, *graph);
678 +
679 + //k 입력
680 + bool isok = false;
681 +
682 + QInputDialog *inputDialog = new QInputDialog();
683 + //int inputK = inputDialog->getText(nullptr, "Enter target's name", "Start node's name:",
684 + // QLineEdit::Normal, "Akira Idoue", &isok).toStdString();
685 + int inputK = inputDialog->getInt(nullptr, "Enter K", "K:", 3,
686 + 1, whole_node_cnt, 1, &isok);
687 + if (!isok) {
688 + qDebug("input cancelled");
689 + return;
690 + }
691 +
692 + //저자별 논문 수 계산 + TopK Heap 사용
693 + //pair -> <num_of_record, label>
694 + TopKHeap<pair<int, string>> heap(inputK);
695 + for (boost::tie(vi, vi_end) = boost::vertices(*graph); vi != vi_end; ++vi) {
696 + if (node_type_map[*vi] != NODE_TYPE::NODE_AUTHOR) {
697 + continue;
698 + }
699 +
700 + int record_cnt = 0;
701 + for (boost::tie(ai, ai_end) = boost::adjacent_vertices(*vi, *graph);
702 + ai != ai_end; ++ai) {
703 + if (node_type_map[*ai] == NODE_TYPE::NODE_PAPER) {
704 + ++record_cnt;
705 + }
706 + }
707 +
708 + boost::put(vertex_record, *graph, *vi, record_cnt);
709 + heap.push(make_pair(record_cnt, node_label_map[*vi]));
710 +
711 + //qDebug() << record_cnt;
712 + }
713 +
714 + //get top K records
715 + //pair<int, string> topk_arr[inputK];
716 + pair<int, string> *topk_arr = new pair<int, string>[inputK];
717 + for (int i = 0; i < inputK; ++i) {
718 + topk_arr[i] = heap.pop();
719 + qDebug() << "topk[" << i << "] = " << topk_arr[i].first << ", " << QString::fromStdString(topk_arr[i].second);
720 + }
721 +
722 +
723 + for (auto& n : nodeList) {
724 + auto label = n->getLabel();
725 + n->setColor(QColor(Qt::lightGray));
726 + for (int i = 0; i < inputK; ++i) {
727 + auto& p = topk_arr[i];
728 + if (label.toStdString() == p.second) {
729 + n->setColor(QColor(Qt::red));
730 + break;
731 + }
732 + }
733 + }
734 + delete[] topk_arr;
522 } 735 }
523 736
524 void GraphItem::find_shortest_path() 737 void GraphItem::find_shortest_path()
...@@ -529,8 +742,7 @@ void GraphItem::find_shortest_path() ...@@ -529,8 +742,7 @@ void GraphItem::find_shortest_path()
529 auto node_idx_map = boost::get(vertex_index, *graph); 742 auto node_idx_map = boost::get(vertex_index, *graph);
530 auto node_label_map = boost::get(vertex_name, *graph); 743 auto node_label_map = boost::get(vertex_name, *graph);
531 744
532 - string target_start, 745 + string target_start, target_end;
533 - target_end;
534 746
535 bool isok = false; 747 bool isok = false;
536 748
...@@ -645,6 +857,21 @@ void GraphItem::find_shortest_path() ...@@ -645,6 +857,21 @@ void GraphItem::find_shortest_path()
645 qDebug("* path highlighting end"); 857 qDebug("* path highlighting end");
646 } 858 }
647 859
860 +void GraphItem::reset_color()
861 +{
862 + for (auto& n: nodeList) {
863 + if (n->getType() == NODE_PAPER) {
864 + n->setColor(QColor(Qt::darkGreen));
865 + } else {
866 + n->setColor(QColor(Qt::green));
867 + }
868 + }
869 + for (auto& e: edgeList) {
870 + e->setColor(Qt::black);
871 + e->setWidth(0);
872 + }
873 +}
874 +
648 void GraphItem::test() 875 void GraphItem::test()
649 { 876 {
650 qDebug("* test action start"); 877 qDebug("* test action start");
......
...@@ -27,9 +27,11 @@ public: ...@@ -27,9 +27,11 @@ public:
27 27
28 //methods 28 //methods
29 void might_know(); 29 void might_know();
30 - void reset_color();
31 void topK_highlight_with_total(); 30 void topK_highlight_with_total();
31 + void topK_highlight_with_target();
32 + void topK_using_custom_score();
32 void find_shortest_path(); 33 void find_shortest_path();
34 + void reset_color();
33 35
34 //test 36 //test
35 void test(); 37 void test();
......
...@@ -39,19 +39,25 @@ void MainWindow::createActions() ...@@ -39,19 +39,25 @@ void MainWindow::createActions()
39 readMoreAct->setStatusTip(tr("read more lines from file")); 39 readMoreAct->setStatusTip(tr("read more lines from file"));
40 connect(readMoreAct, &QAction::triggered, this, &MainWindow::read_more); 40 connect(readMoreAct, &QAction::triggered, this, &MainWindow::read_more);
41 41
42 +
42 mightKnowAct = new QAction(tr("Might know"), this); 43 mightKnowAct = new QAction(tr("Might know"), this);
43 mightKnowAct->setStatusTip(tr("highlight a research you might know")); 44 mightKnowAct->setStatusTip(tr("highlight a research you might know"));
44 connect(mightKnowAct, &QAction::triggered, this, &MainWindow::might_know); 45 connect(mightKnowAct, &QAction::triggered, this, &MainWindow::might_know);
45 - topkAct = new QAction(tr("topK"), this); 46 + topkWithTotalAct = new QAction(tr("topK with total"), this);
46 - topkAct->setStatusTip(tr("highlight who was top k papers")); 47 + topkWithTotalAct->setStatusTip(tr("highlight who was top k papers in whole graph"));
47 - connect(topkAct, &QAction::triggered, this, &MainWindow::topk); 48 + connect(topkWithTotalAct, &QAction::triggered, this, &MainWindow::topK_with_total);
48 - resetColorAct = new QAction(tr("Reset colors"), this); 49 + topKWithTargetAct = new QAction(tr("topK with target"), this);
49 - resetColorAct->setStatusTip(tr("Reset all node's color")); 50 + topKWithTargetAct->setStatusTip(tr("highlight who was top k papers in particular range"));
50 - connect(resetColorAct, &QAction::triggered, this, &MainWindow::reset_color); 51 + connect(topKWithTargetAct, &QAction::triggered, this, &MainWindow::topK_with_target);
51 findShortestPathAct = new QAction(tr("Find Shortest Path"), this); 52 findShortestPathAct = new QAction(tr("Find Shortest Path"), this);
52 findShortestPathAct->setStatusTip("Find shortest path between two node"); 53 findShortestPathAct->setStatusTip("Find shortest path between two node");
53 connect(findShortestPathAct, &QAction::triggered, this, &MainWindow::find_shortest_path); 54 connect(findShortestPathAct, &QAction::triggered, this, &MainWindow::find_shortest_path);
54 55
56 + resetColorAct = new QAction(tr("Reset colors"), this);
57 + resetColorAct->setStatusTip(tr("Reset all node's color"));
58 + connect(resetColorAct, &QAction::triggered, this, &MainWindow::reset_color);
59 +
60 +
55 testAct = new QAction(tr("test action"), this); 61 testAct = new QAction(tr("test action"), this);
56 testAct->setStatusTip(tr("test test")); 62 testAct->setStatusTip(tr("test test"));
57 connect(testAct, &QAction::triggered, this, &MainWindow::test); 63 connect(testAct, &QAction::triggered, this, &MainWindow::test);
...@@ -64,10 +70,12 @@ void MainWindow::createMenus() ...@@ -64,10 +70,12 @@ void MainWindow::createMenus()
64 70
65 actionMenu = menuBar()->addMenu(tr("&Actions")); 71 actionMenu = menuBar()->addMenu(tr("&Actions"));
66 actionMenu->addAction(mightKnowAct); 72 actionMenu->addAction(mightKnowAct);
67 - actionMenu->addAction(topkAct); 73 + actionMenu->addAction(topkWithTotalAct);
68 - actionMenu->addAction(resetColorAct); 74 + actionMenu->addAction(topKWithTargetAct);
69 actionMenu->addAction(findShortestPathAct); 75 actionMenu->addAction(findShortestPathAct);
70 76
77 + actionMenu->addAction(resetColorAct);
78 +
71 testMenu = menuBar()->addMenu(tr("&Test")); 79 testMenu = menuBar()->addMenu(tr("&Test"));
72 testMenu->addAction(testAct); 80 testMenu->addAction(testAct);
73 } 81 }
...@@ -86,14 +94,14 @@ void MainWindow::might_know() ...@@ -86,14 +94,14 @@ void MainWindow::might_know()
86 graphWidget->might_know(); 94 graphWidget->might_know();
87 } 95 }
88 96
89 -void MainWindow::topk() 97 +void MainWindow::topK_with_total()
90 { 98 {
91 graphWidget->topk_with_total(); 99 graphWidget->topk_with_total();
92 } 100 }
93 101
94 -void MainWindow::reset_color() 102 +void MainWindow::topK_with_target()
95 { 103 {
96 - graphWidget->reset_color(); 104 + graphWidget->topk_with_target();
97 } 105 }
98 106
99 void MainWindow::find_shortest_path() 107 void MainWindow::find_shortest_path()
...@@ -101,6 +109,11 @@ void MainWindow::find_shortest_path() ...@@ -101,6 +109,11 @@ void MainWindow::find_shortest_path()
101 graphWidget->find_shortest_path(); 109 graphWidget->find_shortest_path();
102 } 110 }
103 111
112 +void MainWindow::reset_color()
113 +{
114 + graphWidget->reset_color();
115 +}
116 +
104 void MainWindow::test() 117 void MainWindow::test()
105 { 118 {
106 graphWidget->test(); 119 graphWidget->test();
......
...@@ -22,7 +22,8 @@ private: ...@@ -22,7 +22,8 @@ private:
22 QAction *readMoreAct; 22 QAction *readMoreAct;
23 QMenu *actionMenu; 23 QMenu *actionMenu;
24 QAction *mightKnowAct; 24 QAction *mightKnowAct;
25 - QAction *topkAct; 25 + QAction *topkWithTotalAct;
26 + QAction *topKWithTargetAct;
26 QAction *resetColorAct; 27 QAction *resetColorAct;
27 QAction *findShortestPathAct; 28 QAction *findShortestPathAct;
28 29
...@@ -37,9 +38,10 @@ private: ...@@ -37,9 +38,10 @@ private:
37 private slots: 38 private slots:
38 void read_more(); 39 void read_more();
39 void might_know(); 40 void might_know();
40 - void topk(); 41 + void topK_with_total();
41 - void reset_color(); 42 + void topK_with_target();
42 void find_shortest_path(); 43 void find_shortest_path();
44 + void reset_color();
43 //test 45 //test
44 void test(); 46 void test();
45 }; 47 };
......
...@@ -63,6 +63,12 @@ void PaperGraphWidget::topk_with_total() ...@@ -63,6 +63,12 @@ void PaperGraphWidget::topk_with_total()
63 scene->update(); 63 scene->update();
64 } 64 }
65 65
66 +void PaperGraphWidget::topk_with_target()
67 +{
68 + graphItem->topK_highlight_with_target();
69 + scene->update();
70 +}
71 +
66 void PaperGraphWidget::find_shortest_path() 72 void PaperGraphWidget::find_shortest_path()
67 { 73 {
68 graphItem->find_shortest_path(); 74 graphItem->find_shortest_path();
......
...@@ -17,6 +17,7 @@ public: ...@@ -17,6 +17,7 @@ public:
17 void read_more(); 17 void read_more();
18 void might_know(); 18 void might_know();
19 void topk_with_total(); 19 void topk_with_total();
20 + void topk_with_target();
20 void find_shortest_path(); 21 void find_shortest_path();
21 void reset_color(); 22 void reset_color();
22 23
......
...@@ -104,10 +104,10 @@ namespace { ...@@ -104,10 +104,10 @@ namespace {
104 //const int SCREEN_SIZE = 3000; 104 //const int SCREEN_SIZE = 3000;
105 const int SCREEN_SIZE = 500; 105 const int SCREEN_SIZE = 500;
106 //const int READ_LINE_UNIT = 20; //한 번에 몇 라인을 읽을지 106 //const int READ_LINE_UNIT = 20; //한 번에 몇 라인을 읽을지
107 - const int READ_LINE_UNIT = 40; 107 + const int READ_LINE_UNIT = 100;
108 108
109 /* topK */ 109 /* topK */
110 - const int TOP_K = 5; //상위 몇 개 아이템에 대해 highlight 할 지 110 + //const int TOP_K = 5; //상위 몇 개 아이템에 대해 highlight 할 지
111 111
112 /* a research you might know */ 112 /* a research you might know */
113 //const char* TARGET_AUTHOR_NAME = "Shuichi Itoh"; 113 //const char* TARGET_AUTHOR_NAME = "Shuichi Itoh";
...@@ -200,4 +200,6 @@ public: ...@@ -200,4 +200,6 @@ public:
200 return ret; 200 return ret;
201 } 201 }
202 } 202 }
203 + int getSize() {return size;}
204 + bool isFull() {return k==size;}
203 }; 205 };
...\ No newline at end of file ...\ No newline at end of file
......