UVa 215 - Spreadsheet Calculator

时间限制:3.000秒

题目链接:http://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&category=24&page=show_problem&problem=151


  数据结构+模拟。

  给出一个R行C列的电子表格,行编号A~T, 列编号0~9,按照行优先的顺序给出各个单元格。每个单元格可能是整数也可能是引用了其他单元格的表达式,表达式仅由加减号、非负整数、单元格名称组成,没有括号,且以单元格名称开头,内部不含空白符,最多75个字符。要求计算出所有单元格的值,如果所有的单元格都能成功计算出结果,那么将这张表格输出来,每个元素6个占字符的宽度,对齐。如果出现单元格循环引用以致无法输出,则将无法正常计算出结果的单元格及其表达式输出,仍按照行优先的顺序输出。详细格式参见样例。

  按照题意模拟即可,需要注意的地方有表达式的读取以及数据结构的选用。

  这里先将表达式中数字部分先保存在表中,然后将表达式中对单元格的引用单独保存起来,读取全部输入之后dfs计算结果,如果循环则将对应单元格标记为计算失败,并将结果放入set中,最后输出即可。


#include 
#include 
#include 
#include 
#include 
#include 
#include 
#include 

using namespace std;

int r, c, size;

vector > pt[256];
int ss[256];
string ss_s[256];

bool ok_all;
set put_false;

bool ok[256];
bool vis[256];
int dfs(const int &pos) {
    if(!ok[pos]) {
        ok_all = false;
        return 0;
    }
    if(pt[pos].empty()) return ss[pos];
    if(vis[pos]) {
        ok[pos] = false;
        ok_all = false;
        put_false.insert(pos);
        return 0;
    }

    vis[pos] = true;
    for(auto it = pt[pos].begin(); it != pt[pos].end(); ++it) {
        if(ok[it->first]) ss[pos] += (it->second) * dfs(it->first);
        if(!ok[it->first]) {
            ok[pos] = false;
            ok_all = false;
            put_false.insert(pos);
        }
    }
    pt[pos].clear();
    return ss[pos];
}

int main() {
    ios::sync_with_stdio(false);
    while(cin >> r >> c && r && c) {
        size = r * c;
        for(int i = 0; i != size; ++i) {
            pt[i].clear();
            ss[i] = 0;

            string ele; cin >> ele;
            ss_s[i] = ele;

            vector sign;

            if(ele[0] == '-') sign.push_back(-1);
            else sign.push_back(1);
            for(auto it = ele.begin(); it != ele.end(); ++it) {
                if(*it == '-') sign.push_back(-1), *it = ' ';
                else if(*it == '+') sign.push_back(1), *it = ' ';
            }

            istringstream line(ele); auto it = sign.begin();
            while(line >> ele) {
                if(isdigit(ele[0])) {
                    istringstream t(ele);
                    int d; t >> d; ss[i] += d * (*it++);
                } else {
                    int pos = (ele[0] - 'A') * c + ele[1] - '0';
                    pt[i].push_back(pair(pos, *it++));
                }
            }
        }

        ok_all = true;
        put_false.clear();
        for(int i = 0; i != size; ++i) ok[i] = true, vis[i] = false;

        for(int i = 0; i != size; ++i) dfs(i);

        if(!ok_all) {
            for(auto it = put_false.begin(); it != put_false.end(); ++it) cout << (char)(*it / c + 'A') << *it % c << ": " << ss_s[*it] << endl;
        } else {
            cout << ' '; for(int i = 0; i != c; ++i) cout << setw(6) << i; cout << endl;
            for(int i = 0; i != r; ++i) {
                cout << (char)(i + 'A');
                for(int j = 0; j != c; ++j) cout << setw(6) << ss[i * c + j]; cout << endl;
            }
        }

        cout << endl;
    }
}

你可能感兴趣的:(-,-,-,-,UVA,-,-,题目,算法竞赛及其相关)