Каковы наиболее угрозы использования такой реализации подкачки? Помимо безопасности потоков и плохой оптимизации. Когда это терпит неудачу (контрпример)?
template<typename T>
void swapViaMemory(T& left, T& right) {
if(&left == &right) { return ; }
unsigned int tSize = sizeof(T);
unsigned char* lPtr = reinterpret_cast<unsigned char*>(&left);
unsigned char* rPtr = reinterpret_cast<unsigned char*>(&right);
for(unsigned int i = 0; i < tSize; ++i) {
*(lPtr + i) ^= *(rPtr + i);
*(rPtr + i) ^= *(lPtr + i);
*(lPtr + i) ^= *(rPtr + i);
}
}
Извините за грамматические ошибки и орфографические ошибки (=
Если T
содержит элемент, который является указателем или ссылкой на другой из его элементов, это потерпит неудачу (при условии, что цель состоит в том, чтобы указатель / элемент ссылки всегда указывал / ссылался на элемент данных, принадлежащий этому экземпляру).
struct foo
{
foo() : i(), ref_i(i), ptr_i(&i) {}
int i;
int& ref_i;
int *ptr_i;
};
Если два foo
объекты, скажем f1
& f2
поменялись местами с помощью swapViaMemory
после обмена, f1.ref_i
а также f1.ptr_i
будет ссылаться / указывать на f2.i
и наоборот. Кроме того, в случае ссылочного элемента это вызывает неопределенное поведение, поскольку повторное размещение ссылки является незаконным.
Он вызывает неопределенное поведение, если T не является тривиально копируемым типом.
Это не в передаче намерений.
Что является основной целью кода.
template<typename T>
typename std::enable_if<std::is_pod<T>, void>::type
swapViaMemory(T& left, T& right)
{
using std::swap;
swap(left, right);
}
Скажи для:
struct B{
virtual ~B() {}
};
struct X : B
{
int x;
~X() { std::cout << x; }
};
struct Y : B
{
};
//...
X x = X();
Y y;
swapViaMemory<B>(x,y);
Помимо того, что он ужасно запутан, он терпит неудачу, если приведенные слева и справа указывают на один и тот же адрес.
поскольку a^a = 0
(что вы используете для этого «трюка»)
Если left == right
(и давайте предположим, что это 1-байтовая сущность, содержащая 'a'
Тогда вы будете делать:
a^a = 0
0^a = a
a^a = 0