模拟_模拟makefile文件(HDU_4724)

 这题坑爹,说好的五百组呢?

There are at most 500 target in the Makefile. !!!!!

If You Know This,You Must Have NO GF

http://acm.hdu.edu.cn/showproblem.php?pid=4724

#pragma warning(disable : 4786)
#include <iostream>
#include <string>
#include <set>
#include <map>
using namespace std;

typedef string String;
#define M 5050

map<String,int> Com;
set<String> haveFile;
set<String> fileLink[M];
int addI,re_n;

void clear()
{
    Com.clear();
    haveFile.clear();
    for(int i=0; i<M; i++)
    {
        fileLink[i].clear();
    }
    addI = 0;
}

void catString(String &s1)
{
    String s2;
    if(s1[s1.length() - 1] == '\')
    {
        s1[s1.length() - 1] = ' ';
        while(getline(cin,s2))
        {
            s1 += s2;
            if(s1[s1.length() - 1] == '\')
            {
                s1[s1.length() - 1] = ' ';
            }
            else
            {
                break;
            }
        }
    }
}

void eraseString(String &s1)    //erase #~
{
    int finded = s1.find('#',0);
    if(finded != String::npos)
    {
        s1.erase(finded,s1.length() - finded);
    }
}

void addCom(String s1)
{
//    cout << "addCom: |" << s1 << "|" << endl;
    String s2;
    bool flag = true;
    for(int i=0; i<s1.length(); i++)
    {
        if(s1[i] == ' ' || i == s1.length() - 1)
        {
            if(i == s1.length() - 1 && s1[i] != ' ')
            {
                s2 += s1[i];
            }
            if(s2 != "")
            {
                if(flag)
                {
                    flag = false;
                    s2.erase(s2.length() - 1);
                    Com.insert(pair<String,int>(s2,addI));
                }
                else
                {
                    fileLink[addI].insert(s2);
                }
//                cout << "s2:|" << s2 << "|" << endl;
            }
            s2 = "";
        }
        else
        {
            s2 += s1[i];
        }
    }
    addI++;
}

void addFile(String s1)
{
    int finded = s1.find(' ',0);
    if(finded != String::npos)
    {
        s1.erase(finded,s1.length() - finded);
    }
    haveFile.insert(s1);
//    cout << "addFile: |" << s1 << "|" << endl;
}

bool findRun(String s1)
{
//    cout << "findRun:" << s1 << endl;

    if(re_n == -1)    return false;
    if(haveFile.find(s1) != haveFile.end())
        return true;
    if(Com.find(s1) == Com.end())
        return false;
    set<String> t = fileLink[Com[s1]];
    for(set<String>::iterator i = t.begin(); i != t.end(); i++)
    {
        if(findRun(*i) == false)
        {
            re_n = -1;
            return false;
        }
    }
    re_n++;
    haveFile.insert(s1);
    return true;
}

void run(String s1)
{
    String s2;
//    cout << "run: " << s1 << "|" << endl;
    for(int i=0; i<s1.length(); i++)
    {
        if(s1[i] == ' ' || i == s1.length() - 1)
        {
            if(i == s1.length() - 1 && s1[i] != ' ')
            {
                s2 += s1[i];
            }
            if(s2 != "")
            {
                if(s2 != "make")
                {
//                    cout << "s2:|" << s2 << "|" << endl;
                    findRun(s2);
                }
            }
            s2 = "";
        }
        else
        {
            s2 += s1[i];
        }
    }
}

int main(int argc, char* argv[])
{
#ifdef __MYLOCAL
    freopen("in.txt","r",stdin);
#endif
    
    int t;
    cin >> t;
    
    String s1;
    for(int i=1; i<=t; i++)
    {
        clear();
        int n;
        getchar();
        while(getline(cin,s1))
        {
            if(s1 == "====")
                break;
            catString(s1);
            eraseString(s1);
            if(s1.find("g++",0) == String::npos)
                addCom(s1);
//            cout << "comd: " << s1 <<endl;
        }
        cin >> n;
        getchar();
        while(n--)
        {
            getline(cin,s1);
            catString(s1);
            eraseString(s1);
            addFile(s1);
//            cout << "file: " << s1 <<endl;
        }
        cin >> n;
        getchar();
        cout << "Case #" << i << ":" << endl;
        while(n--)
        {
            re_n = 0;
            getline(cin,s1);
            catString(s1);
            eraseString(s1);
            run(s1);
            if(re_n == -1)
                re_n++;
            cout << re_n << endl;
//            cout << "run: " << s1 <<endl;
        }
        if(i != t) cout << endl;
    }
    
    return 0;
}

 以下不受案例数限制,但效率低一点

#pragma warning(disable : 4786)
#include <iostream>
#include <string>
#include <vector>
#include <set>
#include <map>
using namespace std;

typedef string String;

map<String,vector<String> > command;
set<String> haveFile;
int re_n;

void clear()
{
    for(map<String,vector<String> >::iterator iter = command.begin(); iter != command.end(); iter++)
    {
        iter->second.clear();
    }
    command.clear();
    haveFile.clear();
}

void catString(String &s1)
{
    String s2;
    if(s1[s1.length() - 1] == '\')
    {
        s1[s1.length() - 1] = ' ';
        while(getline(cin,s2))
        {
            s1 += s2;
            if(s1[s1.length() - 1] == '\')
            {
                s1[s1.length() - 1] = ' ';
            }
            else
            {
                break;
            }
        }
    }
}

void eraseString(String &s1)
{
    int finded = s1.find('#',0);
    if(finded != String::npos)
    {
        s1.erase(finded,s1.length() - finded);
    }
}

void addCommand(String s1)
{
    String s2,commandName;
    vector<String> fileLink;
    bool flag = true;
    for(int i=0; i<s1.length(); i++)
    {
        if(s1[i] == ' ' || i == s1.length() - 1)
        {
            if(i == s1.length() - 1 && s1[i] != ' ')
            {
                s2 += s1[i];
            }
            if(s2 != "")
            {
                if(flag)
                {
                    flag = false;
                    s2.erase(s2.length() - 1);
                    commandName = s2;
                }
                else
                {
                    fileLink.push_back(s2);
                }
            }
            s2 = "";
        }
        else
        {
            s2 += s1[i];
        }
    }
    command.insert(pair<String,vector<String> >(commandName,fileLink));
}

void addFile(String s1)
{
    int finded = s1.find(' ',0);
    if(finded != String::npos)
    {
        s1.erase(finded,s1.length() - finded);
    }
    haveFile.insert(s1);
}

bool findRun(String s1)
{
    if(re_n == -1)    return false;
    if(haveFile.find(s1) != haveFile.end())
        return true;
    if(command.find(s1) == command.end())
        return false;
    vector<String> t = command.find(s1)->second;
    for(vector<String>::iterator i = t.begin(); i != t.end(); i++)
    {
        if(findRun(*i) == false)
        {
            re_n = -1;
            return false;
        }
    }
    re_n++;
    haveFile.insert(s1);
    return true;
}

void run(String s1)
{
    String s2;
    for(int i=0; i<s1.length(); i++)
    {
        if(s1[i] == ' ' || i == s1.length() - 1)
        {
            if(i == s1.length() - 1 && s1[i] != ' ')
            {
                s2 += s1[i];
            }
            if(s2 != "")
            {
                if(s2 != "make")
                {
                    findRun(s2);
                }
            }
            s2 = "";
        }
        else
        {
            s2 += s1[i];
        }
    }
}

int main(int argc, char* argv[]) 
{
#ifdef __MYLOCAL
    freopen("in.txt","r",stdin);
#endif
    
    int t;
    cin >> t;
    
    String s1;
    for(int i=1; i<=t; i++)
    {
        clear();
        int n;
        getchar();
        while(getline(cin,s1))
        {
            if(s1 == "====")
                break;
            catString(s1);
            eraseString(s1);
            if(s1.find("g++",0) == String::npos)
                addCommand(s1);
        }
        cin >> n;
        getchar();
        while(n--)
        {
            getline(cin,s1);
            catString(s1);
            eraseString(s1);
            addFile(s1);
        }
        cin >> n;
        getchar();
        cout << "Case #" << i << ":" << endl;
        while(n--)
        {
            re_n = 0;
            getline(cin,s1);
            catString(s1);
            eraseString(s1);
            run(s1);
            if(re_n == -1)
                re_n++;
            cout << re_n << endl;
        }
        if(i != t) cout << endl;
    }
    
    return 0;
}
原文地址:https://www.cnblogs.com/lk1993/p/3316295.html