我正在阅读c++中的移动语义,并遇到了以下示例作为动机:
template<class T>
void swap(T& a, T& b)
{
T tmp(std::move(a));
a = std::move(b);
b = std::move(tmp);
}
这里说,如果T没有实现移动语义(在复制构造函数和赋值操作符中),那么swap将表现为“正常”的swap:
template<class T>
void swap(T& a, T& b)
{
T tmp(a);
a = b;
b = tmp;
为什么fun(p)可以工作,而fun(&i)不能? #include<iostream>
using namespace std;
void fun(int*& pp)
{
}
int main()
{
int i;
int *p;
fun(p);
fun(&i); // not working... why?
}
我们只能将引用绑定到对象,而不能绑定到文字或更genreal表达式的结果。
int i=42;
double d=1.2;
int &r=10;//error:initializer must be an object.
int &r1=d; //error: initializer must be an int object
虽然我们可以将对常量的引用绑定到对象,但将文字绑定到更通用表达式的结果,如下所示-
int j=45;
double d=1.2;
const int &r2=j; // works
const int &r2=60; //works
c
错误!
$ cat double.cc
#include<iostream>
int main() {
int i = 42;
double &r = i;
}
$ g++ double.cc
double.cc: In function ‘int main()’:
double.cc:5: error: invalid initialization of reference of type ‘double&’
from expression of type ‘int’
$
成功了!
$ cat double.cc
#include<iost
我想有一些关于临时对象的东西我不理解。给定这些关系:
class C {};
class F {
public:
C getC() { return C(); };
};
class N {
public:
N( C & base ){};
};
这是可行的:
N n(C());
这不起作用:
F f;
N n(f.getC()); //compile error
为什么?
我注意到将char赋值给const int&会进行编译,但是将其赋值给int&会导致编译错误。
char c;
int& x = c; // this fails to compile
const int& y = c; // this is ok
我知道这样做不是一种好的做法,但我很好奇为什么会发生这种情况。
我通过查找“赋值给不同类型的引用”、“将字符赋值给整型引用”和“常量引用和非常数引用之间的差异”来寻找答案,并遇到了一些有用的帖子(、、、),但它们似乎没有解决我的问题。
如果这个问题之前已经回答过了,我很抱歉。
MS VS x86编译器在以下定义上没有问题,但GCC (ARM)抱怨道。是GCC太傻了,还是MSVS_x86太聪明了?
bool checkPointInside(const CIwVec2& globalPoint) {
return checkPointIn(globalPoint, CIwVec2());
}; /// error: no matching function for call to 'Fair::Sprite::checkPointIn(const CIwVec2&, CIwVec2)'
bool checkPointIn(co
有人概括了"Temporaries are rvalues“这句话。我说“不”,并给了他下面的例子
double k=3;
double& foo()
{
return k;
}
int main()
{
foo()=3; //foo() creates a temporary which is an lvalue
}
我的解释正确吗?
我正在尝试在C++中实现一个复杂的类,并重载算术运算符以及输入/输出的“<<”和“>>”运算符。算术运算符单独运行,级联时也能正常工作-但在尝试执行以下语句时,我无法获得正确的结果:
cout << "something" << complex1 + complex2 << "\n";
其中complex1和complex2是类COMPLEX的对象。
类定义的代码片段:
class COMPLEX{
int a; // Real part
int b
class sampleConstructor {
int x;
public:
//WE COULD DO OVERLOAD CONSTRUCTOR JUST LIKE IN FUNCTIONS | THEY ONLY DIFFERENTIATE IN NO. OF ARGUMENTS AND DATATYPE OF ARGUMENTS JUST LIKE IN FUNCTION
sampleConstructor () { //THIS IS THE DEFAULT CONSTRUCTOR, THIS WILL AUTOMATICALLY INITIALIZE EVERYTHING
以下是代码示例。
a. int ii = 0;
b. const int ci = ii;
c. auto e = &ci; --> e is const int *
d. auto &f = 42; --> invalid initialization of non-const reference of type ‘int&’ from an rvalue of type ‘int’
e. const auto &g = 42 --> ok
观察:
对于子句c)类型const是自动推导的;对于子句d)类型const不是自动推导的;对于子句e)
执行此操作时:
int square(int& x) { return x*x;};
int s = square(40); // This gives error
要解决此问题,请执行以下操作:
int square(const int& x) { return x*x;};
int s = square(40); // This is OK
我知道40是一个常量,但如果我这样做:
const int& x = 40
为什么只有const关键字才可以呢?这是编译器保护没有人可以更改x引用的值的方式吗?
40是一个常量,所以我们甚至不知道它在内存中的位置,但是编译
将一个变量转换为另一个类型是否会返回该变量的临时副本?如果是这样,那么为什么不能将临时变量引用到函数中呢?
void func(int &i) //error converting parameter 1 from int to int&
{
}
int main()
{
double d = 6.8;
func(int(d));
}
我正在阅读理论,并遇到了以下情况
let p = t in t //pattern binding
一个有记录模式的例子
let {l1=x1:S1, l2=x2:S2} = E1 in (x1 x2)
// l1,l2 are lebels, x1,x2 are variables, S1 and S2 are types.
我理解让约束,但不熟悉上面的形式,所以我有点困惑。有人能给我一个真实的例子并解释一下吗?我在网上搜索,但没有看到像上面那样的模式绑定。
我使用Visual Studio 2017版本15.3.1测试了以下代码。
v.push_back(std::move(str1))的工作方式与预期一致。它将str1的内容移动到向量中。
str2是一个常量字符串。由于常量字符串在创建后无法修改,因此我预计v.push_back(std::move(str2))语句将导致编译器警告。然而,令我惊讶的是,没有编译器警告。在进入它之后,我发现push_back(const T&)的重载实际上是调用的。std::move(str2)中的std::move似乎没有效果。
我的问题是:如果试图移动一个常量对象,应该给编译器一个警告吗?
// Co