我正在尝试解析HTML文件以进行C ++分配。任务是展示堆栈;每当我们点击标签时,我们都应该推送到堆栈,然后在找到相应的结束标签时弹出。
老师显然希望我们硬编码一组标签来检测,例如:
// Declare some stacks
Stack html;
Stack div;
...
// When you find an open tag, push to the corresponding stack
if (tagcontents == "html") { html.push(); }
if (tagcontents == "div") { div.push(); }
...
// When you find a close tag, push to the corresponding stack
if (tagcontents == "/html") { html.pop(); }
if (tagcontents == "/div") { div.pop(); }
...
明显的缺点是,如果我想支持all of the tags available in HTML,我可以期望进行大量的冗余编码。老师显然希望我们只选择一小部分可用标签,然后关闭那些,但我认为这是 lame 。由于我很懒(而且我坚信所有程序员都应该这样做),我正试图想出一个动态的解决方案。
这个想法是,每当我遇到一个新标签时,都会为它创建一个堆栈。这将允许我的程序支持任何标记,无论有效性如何。不过,我遇到了一个有趣的理论问题,我甚至不确定该怎么称呼才能研究它。也就是说,我需要使用变量的VALUE作为我实际代码的一部分。 IE:
if (no stack exists named "HTML") { create a stack named "HTML" }
简单来说,我怎么能:
tag = "html";
Stack tag; // make a stack named HTML?
还是有另一种方法吗?任何帮助将不胜感激。如果我无法解决这个问题,我可能只会使用像quitter一样的switch / case语句。
答案 0 :(得分:0)
在std::map<std::string, Stack>
。
答案 1 :(得分:0)
使用地图/无序地图:
std::map <std:string, Stack> myStacks;
然后你可以做
myMastacks[tagcontents].push()
这将初始化密钥的新堆栈(如果尚不存在)。
并在标记的末尾,删除斜杠,检查它是否在地图上,然后你去。
答案 2 :(得分:0)
我会做的不同,更简单,所有标签只有一个堆栈(我认为这是非常合理的,除非你的老师实际上指示你使用多个堆栈):声明一堆字符串。字符串表示标记。您可以使用STL堆栈:
stack<string> my_tags;
my_tags.push("div")
会将“div”推入堆栈。
string tag = my_tags.top();
将查询堆栈的顶部,my_tags.pop()
将从堆栈中弹出顶部项目。很简单: - )
同样,这个解决方案很好,以防您不需要练习多个堆栈,而是检查您在html解析中的位置。
答案 3 :(得分:0)
以下是一个例子:
#include <stdio.h>
#include <map>
#include <string>
#include <list>
#include <iostream>
typedef std::list<std::string> stack;
typedef std::map<std::string, stack> stack_map;
stack_map my_stacks;
stack& getStack(const std::string& stack_name) {
stack_map::iterator it = my_stacks.find(stack_name);
if( it != my_stacks.end() ) {
return it->second;
} else {
my_stacks[stack_name] = stack();
return my_stacks[stack_name];
}
}
...
stack& div_stack = getStack("div");
// and use that for example
div_stack.push_back("some info");
div_stack.push_back("some more info ... ");
div_stack.push_back("s even more ... ");
.....