ArKanjo 0.5.1
A tool for find code duplicated functions in codebases
big_clone_tailor_evaluator.cpp
Go to the documentation of this file.
2
3#include <iomanip>
4#include <iostream>
5
7
8void BigCloneTailorEvaluator::read_clone_labels() {
9 count_of_samples_by_type = std::vector<int>(NUMBER_OF_TYPES);
10 std::vector<std::string> content = Utils::read_file_with_vector(CLONE_LABELS_FILE_PATH);
11 for (auto line : content) {
12 std::vector<std::string> tokens = Utils::split_string(line, ',');
13 if (int(tokens.size()) < 4) {
14 continue;
15 }
16 int id0 = stoi(tokens[0]);
17 int id1 = stoi(tokens[1]);
18 int type = stoi(tokens[3]);
19 if (id0 > id1) {
20 std::swap(id0, id1);
21 }
22 std::pair<int, int> aux = {id0, id1};
23 id_pair_to_type[aux] = type;
24 count_of_samples_by_type[type] += 1;
25 }
26}
27
28int BigCloneTailorEvaluator::path_to_id(Path path) {
29 std::string relative_path = path.relative_path();
30 std::vector<std::string> tokens = Utils::split_string(relative_path, '/');
31 std::string file_name = tokens.back();
32 for (int i = 0; i < int(EXTENSION.size()); i++) {
33 file_name.pop_back();
34 }
35 return stoi(file_name);
36}
37
38std::vector<std::tuple<double, int, int>> BigCloneTailorEvaluator::similar_path_pairs_formated_with_id() {
39 auto similar_path_pairs = similarity_table->get_all_similar_pairs();
40 similarity_table->sort_pairs_by_similarity(similar_path_pairs);
41 std::vector<std::tuple<double, int, int>> ret;
42 for (const auto& similar_pair : similar_path_pairs) {
43 auto id1 = similar_pair.id1;
44 auto id2 = similar_pair.id2;
45 if (id1 > id2) {
46 std::swap(id1, id2);
47 }
48 ret.push_back({similar_pair.similarity, id1, id2});
49 }
50 return ret;
51}
52
53bool BigCloneTailorEvaluator::is_relevant_pair(int id0, int id1) {
54 std::pair<int, int> ids = {id0, id1};
55 return id_pair_to_type.find(ids) != id_pair_to_type.end();
56}
57
58std::set<std::pair<int, int>> BigCloneTailorEvaluator::filter_similar_id_pairs_only_relevant_ones(
59 std::vector<std::pair<int, int>> similar_id_pairs) {
60 std::set<std::pair<int, int>> ret;
61 for (auto [id0, id1] : similar_id_pairs) {
62 if (is_relevant_pair(id0, id1)) {
63 ret.insert({id0, id1});
64 }
65 }
66 return ret;
67}
68
69std::vector<std::pair<int, int>> BigCloneTailorEvaluator::filter_similar_path_pairs_by_similarity(
70 std::vector<std::tuple<double, int, int>> similar_id_pairs,
71 double minimum_similarity) {
72 std::vector<std::pair<int, int>> ret;
73 for (auto [similarity, id0, id1] : similar_id_pairs) {
74 if (similarity >= minimum_similarity) {
75 ret.push_back({id0, id1});
76 }
77 }
78 return ret;
79}
80
81std::vector<int> BigCloneTailorEvaluator::build_frequency_corrected_guessed_by_type(
82 std::vector<std::pair<int, int>> similar_id_pairs) {
83 std::set<std::pair<int, int>> similar_id_pairs_set = filter_similar_id_pairs_only_relevant_ones(similar_id_pairs);
84 std::vector<int> frequency(NUMBER_OF_TYPES);
85 for (auto ids : similar_id_pairs_set) {
86 frequency[id_pair_to_type[ids]] += 1;
87 }
88 // for not clone if it is marked as duplicate count is wrong instead of right
89 frequency[NOT_CLONE_TYPE_ID] *= -1;
90 frequency[NOT_CLONE_TYPE_ID] += count_of_samples_by_type[NOT_CLONE_TYPE_ID];
91 return frequency;
92}
93
94double BigCloneTailorEvaluator::calc_recall(std::vector<int> frequency, int type) {
95 double TP = frequency[type];
96 double FN = count_of_samples_by_type[type] - frequency[type];
97 double recall = TP / (TP + FN);
98 return recall;
99}
100
101void BigCloneTailorEvaluator::print_recall_per_type(std::vector<int> frequency) {
102 std::cout << RECALL_PER_TYPE_PRINT << '\n';
103 for (int type = 0; type < NUMBER_OF_TYPES; type++) {
104 double recall = calc_recall(frequency, type);
105 std::cout << ID_TO_TYPE_LABEL[type] << ' ';
106 std::cout << std::fixed << std::setprecision(2) << recall << '\n';
107 }
108}
109
110void BigCloneTailorEvaluator::evaluate(double minimum_similarity) {
111 std::vector<std::tuple<double, int, int>> similar_id_pairs_similarity = similar_path_pairs_formated_with_id();
112 std::vector<std::pair<int, int>> similar_id_pairs = filter_similar_path_pairs_by_similarity(
113 similar_id_pairs_similarity,
114 minimum_similarity);
115 std::vector<int> frequency = build_frequency_corrected_guessed_by_type(similar_id_pairs);
116 print_recall_per_type(frequency);
117}
118
119BigCloneTailorEvaluator::BigCloneTailorEvaluator(Similarity_Table* _similarity_table) {
120 similarity_table = _similarity_table;
121}
122
123bool BigCloneTailorEvaluator::validate([[maybe_unused]] const ParsedOptions& options) {
124 return true;
125}
126
127bool BigCloneTailorEvaluator::run([[maybe_unused]] const ParsedOptions& options) {
128 read_clone_labels();
129 evaluate(MINIMUM_SIMILARITY_TEMP);
130
131 return true;
132}
BigCloneBench evaluation interface * Provides evaluation metrics compatible with BigCloneBench datase...
bool validate(const ParsedOptions &options) override
Validate the arguments already analyzed.
bool run(const ParsedOptions &options) override
Handles BigCloneBench evaluation command.
Represents a logical path to a function in the codebase.
Definition: path.hpp:26
fs::path relative_path() const
Gets the directory portion of the path.
Definition: path.cpp:15
Represents a similarity graph between functions (paths).
std::vector< SimilarPair > get_all_similar_pairs()
Gets all similar path pairs with scores, sorted.
void sort_pairs_by_similarity(std::vector< SimilarPair > &similar_pairs) const
Sorts path pairs by similarity.
std::vector< std::string > split_string(const std::string &s, char delimiter)
Splits a string by a delimiter into tokens.
Definition: utils.cpp:84
std::vector< std::string > read_file_with_vector(const fs::path &path)
Reads a file line by line into a vector of strings.
Definition: utils.cpp:26
Defines utility functions used across all files.