现在我正在尝试制作一个递归函数,它采用 HTML 文档树并仅使用子 (>
) 运算符返回表示格式化 CSS 的字符串。我会进一步解释,也许你可以帮助我解决问题。至少请给我一些提示或想法。
所以我们的想法是从类似的东西开始
body
/ \
div div
/ \ / \ \
h1 p p ul div
/ \
li li
到
div
div > h1
div > p
div > p
div > ul
div > ul > li
div > ul > li
div > div
或者,如果你愿意,
"div\n\t div > h1\n\tdiv > p\n\tdiv > p\n\tdiv > ul\n\t\tdiv > ul > li\n\t\tdiv > ul > li\n\tdiv > div"
我已经有了一个获取 body
和从中生长的树的过程。我需要的 3 个函数是名为 XMLNode
getChildNode(int k)
返回XMLNode
对象,它是第k
个子对象。如果不存在,则对象返回具有属性isEmpty()
。getName()
将节点的名称作为类似字符串的对象返回,该对象可以转换为字符串。
所以我尝试编写一个执行我需要的过程的尝试是调用
std::cout << tree2CSS(bodyNode);
函数tree2CSS
的实现方式如下
std::string tree2CSS(XMLNode & rootNode, unsigned depth = 0)
{
int i = 1;
XMLNode childNode = rootNode.getChildNode(i);
std::string accumCSS;
while (!childNode.isEmpty())
{
std::string tabs(depth, '\t');
accumCSS.append("\n" + tabs);
if (depth > 0) accumCSS.append(" > ");
accumCSS.append((std::string)childNode.getName() + tree2CSS(childNode, depth + 1));
childNode = rootNode.getChildNode(++i);
}
return accumCSS;
}
问题是,该程序不起作用,我不明白为什么。谁能帮帮我?
最佳答案
您想为每个元素打印整个祖先,因此您必须以某种方式跟踪所有父元素,而不仅仅是深度。
我认为最好为循环外的每个元素处理一次打印,并且循环仅用于访问子元素。
这是一个替代实现:
std::string tree2CSS_(XMLNode& rootNode, std::vector<std::string>& pred)
{
std::string accumCSS(pred.size(), '\t');
std::string name = rootNode.getName();
for (size_t i = 0; i < pred.size(); ++i) {
accumCSS += pred[i] + " > ";
}
accumCSS += name + "\n";
size_t i = 0;
XMLNode& childNode = rootNode.getChildNode(i);
pred.push_back(name);
while (!childNode.isEmpty()) {
accumCSS.append(tree2CSS_(childNode, pred));
childNode = rootNode.getChildNode(++i);
}
pred.pop_back();
return accumCSS;
}
std::string tree2CSS(XMLNode& rootNode)
{
std::vector<std::string> pred;
return tree2CSS_(rootNode, pred);
}
我在这里使用了一个由前面的字符串组成的 vector ,其大小当然是递归深度。实现分为提供 vector 的前端函数和递归实现。
此实现打印正文节点并将正文添加到所有 CSS 声明符之前。如果您想跳过最顶层的节点,请在前端函数中循环 body 的子节点。
关于html - 从 HTML 文档树打印 CSS 的算法,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27370764/