Home » U++ Library support » U++ Core » Vector<T>::Set(int i, T&& x) proposal
Vector<T>::Set(int i, T&& x) proposal [message #49119] |
Tue, 19 December 2017 23:30  |
Novo
Messages: 1430 Registered: December 2006
|
Ultimate Contributor |
|
|
I propose to add method below to the Vector class.
template <class T>
T& Vector<T>::Set(int i, T&& x) {
ASSERT(i >= 0);
const int count = GetCount();
if (i == count)
return Add(pick(x));
else if (i > count) {
At(i - 1);
return Add(pick(x));
}
T* addr = vector + i;
addr->~T();
::new(addr) T(pick(x));
return *addr;
}
Or it can be implemented like this:
template <class T>
T& Vector<T>::Set(int i, T&& x) {
ASSERT(i >= 0);
At(i);
T* addr = vector + i;
addr->~T();
::new(addr) T(pick(x));
return *addr;
}
Second implementation has less memory allocation stuff. It is hard to tell which one is better.
I believe there is no need to check that x is already contained in Vector because it is impossible to get an rvalue of a Vectors's element.
Regards,
Novo
|
|
|
|
Re: Vector<T>::Set(int i, T&& x) proposal [message #49345 is a reply to message #49336] |
Tue, 30 January 2018 03:30   |
Novo
Messages: 1430 Registered: December 2006
|
Ultimate Contributor |
|
|
mirek wrote on Sun, 28 January 2018 16:47I am considering this, but single element Set was always just v.At(i) = pick(src);
Well, yes. This will work as well. But this is significantly less intuitive. Your way of solving this problem definitely didn't come to my mind when I was looking for a solution. Adding of an rvalue-based version of Set definitely won't break API because you already have a reference-based version. This is just another performance optimization.
My solution is based on move-constructor and yours is based on move-operator.
Regards,
Novo
[Updated on: Tue, 30 January 2018 03:45] Report message to a moderator
|
|
|
Re: Vector<T>::Set(int i, T&& x) proposal [message #49366 is a reply to message #49345] |
Wed, 31 January 2018 19:34   |
 |
mirek
Messages: 14255 Registered: November 2005
|
Ultimate Member |
|
|
Novo wrote on Tue, 30 January 2018 03:30mirek wrote on Sun, 28 January 2018 16:47I am considering this, but single element Set was always just v.At(i) = pick(src);
Well, yes. This will work as well. But this is significantly less intuitive. Your way of solving this problem definitely didn't come to my mind when I was looking for a solution. Adding of an rvalue-based version of Set definitely won't break API because you already have a reference-based version. This is just another performance optimization.
My solution is based on move-constructor and yours is based on move-operator.
OK. After further thinking, for some time now I think it is worthwhile to add
const T& Vector::Get(int i, const T& default) { return i >= 0 && i < GetCount() ? Get(i) : default; }
Set makes a nice complement to this, so it makes sense to add Set(int, T&&) too.
Do you see any problem with trivial implementation
void Vector::Set(int i, T&& x) { At(i) = pick(x); }
?
BTW, this is simple. But if I am about to add it here, I have to do that for every container where it makes sense and fill documentation too, add autotests. Thats just to explain my hesitation...
|
|
|
Re: Vector<T>::Set(int i, T&& x) proposal [message #49368 is a reply to message #49366] |
Wed, 31 January 2018 20:01   |
Novo
Messages: 1430 Registered: December 2006
|
Ultimate Contributor |
|
|
mirek wrote on Wed, 31 January 2018 13:34
Do you see any problem with trivial implementation
void Vector::Set(int i, T&& x) { At(i) = pick(x); }
IMHO, it should look like below.
T& Vector::Set(int i, T&& x) { return At(i) = pick(x); }
My current coding pattern (without the T&& version) looks like that:
T& v = vector.At(ind) = T(args);
Regards,
Novo
|
|
|
|
|
Goto Forum:
Current Time: Fri Apr 25 19:04:59 CEST 2025
Total time taken to generate the page: 0.00994 seconds
|