在 C++ 中打印变量所属函数的名称

Print name of the function that the variables belong to in C++

我在尝试解决这个问题时遇到了很多麻烦。我必须读取一个具有三个函数(add、sub 和 main)的 .c 文件,我想将它们的变量名称打印到控制台,并将函数名称放在括号中。我尝试在我的结构中实现一个字符串 function_name 来存储函数的值,但我不知道如何在我的变量旁边打印它,直到我点击另一个函数。任何帮助或建议将不胜感激。

例如:

来自这个 .c 文本

int add ( int a , int b )
{
    return a + b ;
}

我想要这个:

add, line 1, function, int, referenced 2
a (add), line 1, variable, int, referenced 1 
b (add), line 1, variable, int, referenced 1

但我明白了:

add(add), line 1, function, int, referenced 16
a, line 1, variable, int, referenced 15
b, line 1, variable, int, referenced 15

到目前为止,我的代码如下所示。

#include <iostream>
#include <string>
#include <fstream>
#include <sstream>
#include <vector>

using namespace std;

struct identifier
{
    string id_name; 
    string function_name;
    int id_count; 
    string id_function;
    string id_type;
    int id_ref;

};

int main(int argc, char** argv)
{
    
    
    if (argc < 2)
    {
        cout << "ERROR: There is no file selected." << endl;
    }
    
    ifstream file(argv[1]);
    string line;
    string token;
    vector<identifier> id_list;

    int line_counter = 0;
    int num_functions = 0;
    int num_variables = 0;
    int num_if = 0;
    int num_for = 0;
    int num_while = 0;
    

    while (getline(file, line))
    {
        stringstream stream(line);

        line_counter++;

        while (stream >> token)
        {
           bool found = false;
            for (auto& v : id_list)
            {
                if (v.id_name == token)
                {
                    //We have seen the word so add one to its count
                    v.id_ref++;
                    found = true;
                    break;
                }
            }
           if (token == "int" || token == "int*")
            {
                string star = token;
                identifier intI;

                stream >> token;
                string name = token;
               
                intI.id_name = name;
                intI.id_count = line_counter;
                intI.id_type = "int";
               
                stream >> token; //Get the next token
                if (token == "(")
                {
                    //We have a function
                    intI.id_function = "function";
                    
                    if (intI.id_name != "main")
                    {
                        intI.function_name = "(" + name + ")";
                    }
                    
                    num_functions++;
                }
                else
                {
                    //We have a variable
                    intI.id_function = "variable";

                    if (star == "int*")
                    {
                        intI.id_type = "int*";
                    }

                    num_variables++;
                }
                 id_list.push_back(intI);
            }
        }
    file.close();
    //Print the words and their counts
   
    for (auto& v : id_list)
    {
      cout << v.id_name << v.function_name << ", line " << v.id_count << ", " << v.id_function << ", " << v.id_type << ", referenced " << v.id_ref << endl;
    }

    return 0;

我可以看到您现在正在递增 id_ref,但它仍未初始化,因此您有未定义的行为。最简单的方法是在 struct.

中定义的地方执行 = 0;

至于你的函数,假设这里没有嵌套函数,那么你可以只使用一个变量来跟踪它。

#include <iostream>
#include <string>
#include <fstream>
#include <sstream>
#include <vector>

struct identifier {
    std::string id_name;
    std::string function_name;
    int id_count;
    std::string id_function;
    std::string id_type;
    int id_ref = 0; // if not initialized, then you will get seemingly random numbers

};

int main( int argc, char **argv ) {


    if ( argc < 2 )     {
        std::cout << "ERROR: There is no file selected." << std::endl;
        return 1; // quit early
    }

    std::ifstream file( argv[1] );
    std::string line;
    std::string token;
    std::vector<identifier> id_list;

    int line_counter = 0;
    int num_functions = 0;
    int num_variables = 0;
    int num_if = 0;
    int num_for = 0;
    int num_while = 0;

    std::string current_function; // keep track of the function


    while ( std::getline( file, line ) ) {
        std::stringstream stream( line );

        line_counter++;

        while ( stream >> token ) {
            bool found = false;
            for ( auto &v : id_list ) {
                if ( v.id_name == token ) {
                    //We have seen the word so add one to its count
                    v.id_ref++;
                    found = true;
                    break;
                }
            }
            if ( token == "int" || token == "int*" ) {
                std::string star = token;
                identifier intI;

                stream >> token;
                std::string name = token;

                intI.id_name = name;
                intI.id_count = line_counter;
                intI.id_type = "int";

                stream >> token; //Get the next token
                if ( token == "(" ) {
                    //We have a function
                    intI.id_function = "function";

                    if ( intI.id_name != "main" ) {
                        current_function = name; // update the current function name

                    }

                    num_functions++;
                } else {
                    intI.function_name = "(" + current_function + ")"; // add the function name to the variable name
                    //We have a variable
                    intI.id_function = "variable";

                    if ( star == "int*" ) {
                        intI.id_type = "int*";
                    }

                    num_variables++;
                }
                id_list.push_back( intI );
            }
        }
    }
    //file.close();
    //Print the words and their counts

    for ( const auto &v : id_list ) {
        std::cout << v.id_name << v.function_name << ", line " << v.id_count << ", " << v.id_function << ", " << v.id_type << ", referenced " << v.id_ref << std::endl;
    }

    return 0;
}

还有一些recommended reading on using namespace std

工作示例修改为使用字符串而不是参数:https://godbolt.org/z/jKqqrhce6