我刚刚发现了最令人困惑的错误,我不明白为什么编译器没有为我标记它.如果我写下面的内容:
string s = "abcdefghijkl";
cout << s << endl;
s.substr(2,3) = "foo";
s.substr(8,1) = '.';
s.substr(9,1) = 4;
cout << s << endl;
Run Code Online (Sandbox Code Playgroud)
编译器对此没有任何问题,并且赋值语句似乎根据打印出的内容没有任何效果.相反,
s.front() = 'x';
Run Code Online (Sandbox Code Playgroud)
具有我期望的效果(因为front
返回对字符的引用)改变底层字符串,和
s.length() = 4;
Run Code Online (Sandbox Code Playgroud)
也有产生编译器错误的预期效果,抱怨你不能分配给不是左值的东西,因为length
返回一个整数.(好吧,size_t
无论如何.)
那么......为什么编译器不会抱怨分配给substr
调用的结果呢?它返回一个字符串值,而不是引用,所以它不应该是可赋值的,对吧?但我在g++
(6.2.1)和clang++
(3.9.0)中尝试了这个,所以它似乎不是一个bug,它似乎也不敏感C++版本(试过03,11,14) ).
在什么情况下,额外的分组括号会破坏C++中的内容(特别是C++ 11)?由于这里不相关的原因,我最终在一个表达式上有一个额外的,不必要的一组parens围绕它,我发现C++ 11 typeinfo函数is_same
确定它是一个不同于没有括号的相同代码.这是一个有点莫名其妙的行为的简要示例:
#include <iostream>
using namespace std;
int main()
{
string s = "foo";
cout << std::is_same<decltype(s), decltype(string("foo"))>::value;
cout << std::is_same<decltype(s), decltype((s))>::value;
cout << std::is_same<decltype((s)), decltype(string("foo"))>::value;
cout << std::is_same<decltype((s)+"x"), decltype(string("foo")+"x")>::value;
return 0;
}
Run Code Online (Sandbox Code Playgroud)
此代码打印"1001",这似乎表示中间两行中的额外parens导致表达式为不同类型,但在较大的表达式中使用该括号表达式使其再次成为相同类型.另一方面,如果我使用typeid获取类型的名称,typeid(s)
并且typeid((s))
似乎产生相同的东西.
我现在已经解决了眼前的问题,但我仍然不明白为什么会发生这种情况; 搜索"双括号c ++"之类的东西似乎没有出现任何相关内容(主要是有关运算符重载的页面,以及仅在特定关键字后激活的编译器扩展).
那么:这到底是怎么回事?为什么类型s
不同(s)
?
我有一个我想要显示的网址/标题对值列表.(更具体地说,每个对象都有自己的链接列表,一些有0,有些有1,有些有更多.)我希望它们出现在逗号分隔的列表中.所以我在.erb文件中写了这个:
<%= links.map{|wl| link_to wl.title, wl.url}.join(', ') %>
Run Code Online (Sandbox Code Playgroud)
令我惊讶的是,这显示了我想要创建的链接的HTML代码的逗号分隔列表; 也就是说,它采用了所有尖括号和&符号编码.为了确保高阶函数没有任何有趣的东西,我尝试了一个更为迫切的版本:
<% a = [] %>
<% links.each do |wl| %>
<% a << link_to(wl.title, wl.url) %>
<% end %>
<%= a.join(', ') %>
Run Code Online (Sandbox Code Playgroud)
当然,结果相同.但我不认为我在滥用link_to
,因为如果我修改它
<% links.each do |wl| %>
<%= link_to(wl.title, wl.url) %>,
<% end %>
Run Code Online (Sandbox Code Playgroud)
然后它实际上创建了链接.它几乎就是我想要的,除了在最后一个之后还有一个额外的逗号.引擎盖下是否有一些魔法可以link_to
根据其输出的前进方式采取不同的行动?有没有办法绕过那个魔法?该join
语义是什么我想在这里,我可以明显地弄清楚如何推出自己的(使用each_index,我猜),但它似乎是一个非常沉重的和未红宝石解决什么必须是一个常见的问题.
我的理解是,样式化的元素display:inline-block
将在内部布局为一个块,但在它们所在的任何容器中被视为内联元素。如果它们位于一个li
或一个div
或一堆其他事物中,这似乎是正确的;但如果它们在里面,那就p
不同了,原因我不清楚。考虑以下示例:
<!DOCTYPE html>
<p>Test1<table style="display:inline-block"><tr><td>x</td></tr></table>Test1</p>
<div>Test2<table style="display:inline-block"><tr><td>x</td></tr></table>Test2</div>
<p>Test3<span style="display:inline-block"><table><tr><td>x</td></tr></table></span>Test3</p>
<div>Test4<span style="display:inline-block"><table><tr><td>x</td></tr></table></span>Test4</div>
Run Code Online (Sandbox Code Playgroud)
这里,前两行有一个表,display:inline-block
其样式分别位于 ap
和 a内部div
。接下来的两个表在span
具有内联块样式的 a 内,同样在 ap
和 a内div
。在测试 2 和测试 4 的div
情况下,整个事情都显示在一行上(正如我对所有这些情况所期望的那样)。在 Test1 中,假定的内联块元素前面有一个换行符,而在 Test3 中,假定的内联块元素前面和后面都有一个换行符。
为什么?