Wednesday, December 18, 2019

Digest for comp.lang.c++@googlegroups.com - 23 updates in 4 topics

Mr Flibble <flibbleREMOVETHISBIT@i42.co.uk>: Dec 18 09:34PM

Hi!
 
The following is the base class of my vector class (the mathematical vector not the container) so I can do things like:
 
vec3 v1 = { 1.0, 2.0, 3.0 };
vec2 v2 = v1.xy;
double z = v1.z;
vec4 v3 = v1.xyzz;
 
So we have an anonymous union of an anonymous struct and some swizzles and I suspect it is full of UB but I am finding it hard to care as I cannot see any other way of doing this.
 
Collective thoughts/wisdom?
 
// swizzle_array.hpp
/*
neogfx C++ GUI Library
Copyright (c) 2019 Leigh Johnston. All Rights Reserved.
 
This program is free software: you can redistribute it and / or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
 
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
 
You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
 
#pragma once
 
#include <neogfx/neogfx.hpp>
#include <neogfx/core/swizzle.hpp>
 
namespace neogfx
{
namespace math
{
template <typename V, typename T, uint32_t Size>
struct swizzle_array
{
typedef T value_type;
typedef std::array<value_type, Size> array_type;
typedef V vector_type;
 
union
{
array_type v;
struct // todo: alignment, padding?
{
value_type x;
value_type y;
value_type z;
};
swizzle<vector_type, array_type, 2, 0, 0> xx;
swizzle<vector_type, array_type, 2, 0, 1> xy;
swizzle<vector_type, array_type, 2, 0, 2> xz;
swizzle<vector_type, array_type, 2, 1, 0> yx;
swizzle<vector_type, array_type, 2, 1, 1> yy;
swizzle<vector_type, array_type, 2, 1, 2> yz;
swizzle<vector_type, array_type, 2, 2, 0> zx;
swizzle<vector_type, array_type, 2, 2, 1> zy;
swizzle<vector_type, array_type, 2, 2, 2> zz;
swizzle<vector_type, array_type, 3, 0, 0, 0> xxx;
swizzle<vector_type, array_type, 3, 0, 0, 1> xxy;
swizzle<vector_type, array_type, 3, 0, 0, 2> xxz;
swizzle<vector_type, array_type, 3, 0, 1, 0> xyx;
swizzle<vector_type, array_type, 3, 0, 1, 1> xyy;
swizzle<vector_type, array_type, 3, 0, 1, 2> xyz;
swizzle<vector_type, array_type, 3, 1, 0, 0> yxx;
swizzle<vector_type, array_type, 3, 1, 0, 1> yxy;
swizzle<vector_type, array_type, 3, 1, 0, 2> yxz;
swizzle<vector_type, array_type, 3, 1, 1, 0> yyx;
swizzle<vector_type, array_type, 3, 1, 1, 1> yyy;
swizzle<vector_type, array_type, 3, 1, 1, 2> yyz;
swizzle<vector_type, array_type, 3, 1, 2, 0> yzx;
swizzle<vector_type, array_type, 3, 1, 2, 1> yzy;
swizzle<vector_type, array_type, 3, 1, 2, 2> yzz;
swizzle<vector_type, array_type, 3, 2, 0, 0> zxx;
swizzle<vector_type, array_type, 3, 2, 0, 1> zxy;
swizzle<vector_type, array_type, 3, 2, 0, 2> zxz;
swizzle<vector_type, array_type, 3, 2, 1, 0> zyx;
swizzle<vector_type, array_type, 3, 2, 1, 1> zyy;
swizzle<vector_type, array_type, 3, 2, 1, 2> zyz;
swizzle<vector_type, array_type, 3, 2, 2, 0> zzx;
swizzle<vector_type, array_type, 3, 2, 2, 1> zzy;
swizzle<vector_type, array_type, 3, 2, 2, 2> zzz;
};
};
 
template <typename V, typename T>
struct swizzle_array<V, T, 1>
{
typedef T value_type;
typedef std::array<value_type, 1> array_type;
typedef V vector_type;
 
union
{
array_type v;
struct // todo: alignment, padding?
{
value_type x;
};
swizzle<vector_type, array_type, 2, 0, 0> xx;
swizzle<vector_type, array_type, 3, 0, 0, 0> xxx;
};
};
 
template <typename V, typename T>
struct swizzle_array<V, T, 2>
{
typedef T value_type;
typedef std::array<value_type, 2> array_type;
typedef V vector_type;
 
union
{
array_type v;
struct // todo: alignment, padding?
{
value_type x;
value_type y;
};
swizzle<vector_type, array_type, 2, 0, 0> xx;
swizzle<vector_type, array_type, 2, 0, 1> xy;
swizzle<vector_type, array_type, 2, 1, 0> yx;
swizzle<vector_type, array_type, 2, 1, 1> yy;
swizzle<vector_type, array_type, 3, 0, 0, 0> xxx;
swizzle<vector_type, array_type, 3, 0, 0, 1> xxy;
swizzle<vector_type, array_type, 3, 0, 1, 0> xyx;
swizzle<vector_type, array_type, 3, 0, 1, 1> xyy;
swizzle<vector_type, array_type, 3, 1, 0, 0> yxx;
swizzle<vector_type, array_type, 3, 1, 0, 1> yxy;
swizzle<vector_type, array_type, 3, 1, 1, 0> yyx;
swizzle<vector_type, array_type, 3, 1, 1, 1> yyy;
};
};
 
template <typename V, typename T>
struct swizzle_array<V, T, 3>
{
typedef T value_type;
typedef std::array<value_type, 3> array_type;
typedef V vector_type;
 
union
{
array_type v;
struct // todo: alignment, padding?
{
value_type x;
value_type y;
value_type z;
};
swizzle<vector_type, array_type, 2, 0, 0> xx;
swizzle<vector_type, array_type, 2, 0, 1> xy;
swizzle<vector_type, array_type, 2, 0, 2> xz;
swizzle<vector_type, array_type, 2, 1, 0> yx;
swizzle<vector_type, array_type, 2, 1, 1> yy;
swizzle<vector_type, array_type, 2, 1, 2> yz;
swizzle<vector_type, array_type, 2, 2, 0> zx;
swizzle<vector_type, array_type, 2, 2, 1> zy;
swizzle<vector_type, array_type, 2, 2, 2> zz;
swizzle<vector_type, array_type, 3, 0, 0, 0> xxx;
swizzle<vector_type, array_type, 3, 0, 0, 1> xxy;
swizzle<vector_type, array_type, 3, 0, 0, 2> xxz;
swizzle<vector_type, array_type, 3, 0, 1, 0> xyx;
swizzle<vector_type, array_type, 3, 0, 1, 1> xyy;
swizzle<vector_type, array_type, 3, 0, 1, 2> xyz;
swizzle<vector_type, array_type, 3, 1, 0, 0> yxx;
swizzle<vector_type, array_type, 3, 1, 0, 1> yxy;
swizzle<vector_type, array_type, 3, 1, 0, 2> yxz;
swizzle<vector_type, array_type, 3, 1, 1, 0> yyx;
swizzle<vector_type, array_type, 3, 1, 1, 1> yyy;
swizzle<vector_type, array_type, 3, 1, 1, 2> yyz;
swizzle<vector_type, array_type, 3, 1, 2, 0> yzx;
swizzle<vector_type, array_type, 3, 1, 2, 1> yzy;
swizzle<vector_type, array_type, 3, 1, 2, 2> yzz;
swizzle<vector_type, array_type, 3, 2, 0, 0> zxx;
swizzle<vector_type, array_type, 3, 2, 0, 1> zxy;
swizzle<vector_type, array_type, 3, 2, 0, 2> zxz;
swizzle<vector_type, array_type, 3, 2, 1, 0> zyx;
swizzle<vector_type, array_type, 3, 2, 1, 1> zyy;
swizzle<vector_type, array_type, 3, 2, 1, 2> zyz;
swizzle<vector_type, array_type, 3, 2, 2, 0> zzx;
swizzle<vector_type, array_type, 3, 2, 2, 1> zzy;
swizzle<vector_type, array_type, 3, 2, 2, 2> zzz;
};
};
}
}
 
/Flibble
 
--
"Snakes didn't evolve, instead talking snakes with legs changed into snakes." - Rick C. Hodgin
 
"You won't burn in hell. But be nice anyway." – Ricky Gervais
 
"I see Atheists are fighting and killing each other again, over who doesn't believe in any God the most. Oh, no..wait.. that never happens." – Ricky Gervais
 
"Suppose it's all true, and you walk up to the pearly gates, and are confronted by God," Byrne asked on his show The Meaning of Life. "What will Stephen Fry say to him, her, or it?"
"I'd say, bone cancer in children? What's that about?" Fry replied.
"How dare you? How dare you create a world to which there is such misery that is not our fault. It's not right, it's utterly, utterly evil."
"Why should I respect a capricious, mean-minded, stupid God who creates a world that is so full of injustice and pain. That's what I would say."
"Öö Tiib" <ootiib@hot.ee>: Dec 18 02:24PM -0800

On Wednesday, 18 December 2019 23:35:23 UTC+2, Mr Flibble wrote:
> vec4 v3 = v1.xyzz;
 
> So we have an anonymous union of an anonymous struct and some swizzles and I suspect it is full of UB but I am finding it hard to care as I cannot see any other way of doing this.
 
> Collective thoughts/wisdom?
 
It likely violates strict aliasing, casting between unrelated types
and also how unions are allowed to be used in C++.
 
So even if it appears to work with your compilers on cases
you did test it might mess it up differently in other use-cases
that you did not test yet. Also it may change with next patch to
any of your compilers.
 
Can you say what is the issue with typical interface
implementable to work same on all C++11 or better compilers:
 
vec3 v1 = { 1.0, 2.0, 3.0 };
vec2 v2 = v1.xy();
double z = v1.z();
vec4 v3 = v1.xyzz();
 
Couple of extra parentheses can't be problem, otherwise we all
would switch to Kotlin (that is *way* less verbose than C++).
Mr Flibble <flibbleREMOVETHISBIT@i42.co.uk>: Dec 18 11:14PM

On 18/12/2019 22:24, Öö Tiib wrote:
> vec4 v3 = v1.xyzz();
 
> Couple of extra parentheses can't be problem, otherwise we all
> would switch to Kotlin (that is *way* less verbose than C++).
 
Because
 
v1.set_z(42.0);
 
is ew and
 
v1.z() = 42.0
 
is even more ew.
 
/Flibble
 
--
"Snakes didn't evolve, instead talking snakes with legs changed into snakes." - Rick C. Hodgin
 
"You won't burn in hell. But be nice anyway." – Ricky Gervais
 
"I see Atheists are fighting and killing each other again, over who doesn't believe in any God the most. Oh, no..wait.. that never happens." – Ricky Gervais
 
"Suppose it's all true, and you walk up to the pearly gates, and are confronted by God," Byrne asked on his show The Meaning of Life. "What will Stephen Fry say to him, her, or it?"
"I'd say, bone cancer in children? What's that about?" Fry replied.
"How dare you? How dare you create a world to which there is such misery that is not our fault. It's not right, it's utterly, utterly evil."
"Why should I respect a capricious, mean-minded, stupid God who creates a world that is so full of injustice and pain. That's what I would say."
James Kuyper <jameskuyper@alumni.caltech.edu>: Dec 17 11:55PM -0500

On 12/17/19 9:44 AM, Ben Bacarisse wrote:
> David Brown <david.brown@hesbynett.no> writes:
 
>> On 17/12/2019 05:07, Ben Bacarisse wrote:
...
>> "-std=c11".
 
>> It is an implementation-specific type that handles 128-bit integers, but
>> it is not an "integer type" as defined by the C standards.
 
...
> The only way that it can not be a signed integer type is by a decree
> from gcc.
 
You say that as if you think there's something odd about it. The set of
extended integer types that are supported by a given implementation is
implementation-defined (3.9.1p2). _int128_t fails to be an extended
integer type, despite being a type supported by gcc, because gcc has
exercised it's prerogative of choosing not to define it as an extended
integer type.
 
This has some consequences: _int128_t also cannot be an integer type,
since it isn't any of the other things that can be integer types
(standard integer types, bool, char, char16_t, char32_t, wchar_t). It
also can't be an arithmetic type, because it isn't a floating point
type, the only kind of non-integer type that can be an arithmetic type
(note: n4578.pdf uses the term "arithmetic type" without ever defining
it - I suspect this was an oversight, and the intended definition is
similar to the one provided in the C standard).
 
It also can't be a scalar type, because it certainly doesn't qualify as
an enumerated type, a pointer type, a pointer to member type, or
std::nullptr_t. It can't qualify as a POD type, since it certainly isn't
a POD class type or an array of POD types. Similarly, it isn't a
fundamental type, a trivially-copyable type, a trivial type, or a
standard-layout type, or a literal type.
 
Therefore, when invoked in fully conforming mode, gcc must diagnose any
use of _int128_t in any context where the C++ standard requires a type
that is in one of those categories. When discussing the corresponding
issue in comp.lang.c, I was told that gcc does in fact issue all of the
diagnostics required by the C standard when using _int128_t. I would
presume that it does the same when compiling in C++ mode.
 
After issuing that diagnostic message, the behavior is undefined, so gcc
is free to handle _int128_t exactly the way it would have handled it if
gcc had chosen to define it as being an extended integer type. It's also
free not to define intmax_t as large enough to hold all values that are
representable as _int128_t.
Keith Thompson <Keith.S.Thompson+u@gmail.com>: Dec 17 10:08PM -0800

David Brown <david.brown@hesbynett.no> writes:
[...]
> types. (With the maxint_t issue being another key reason, and lack of
> support in library functions such as printf, *abs, strto*, etc., being
> others.)
 
It's intmax_t, not maxint_t. (I've seen this misspelling several times
in this thread.)
 
--
Keith Thompson (The_Other_Keith) Keith.S.Thompson+u@gmail.com
[Note updated email address]
Working, but not speaking, for Philips Healthcare
void Void(void) { Void(); } /* The recursive call of the void */
David Brown <david.brown@hesbynett.no>: Dec 18 08:56AM +0100

On 18/12/2019 07:08, Keith Thompson wrote:
>> others.)
 
> It's intmax_t, not maxint_t. (I've seen this misspelling several times
> in this thread.)
 
Yes, of course. It's obvious when you use it (it's an "intXXX_t" type),
but it's easy to mix when typing a post. Sorry if I have caused
confusion by my misspellings.
boltar@nowhere.co.uk: Dec 18 04:14PM

On Tue, 17 Dec 2019 19:35:00 +0200
 
>>> To have non-POD types, obviously! And for speed, of course.
 
>> You've never done any embedded development have you.
 
>Ah, trying to change the topic and ad hominem in a single line. Well done!
 
I suggest you go look up what ad hominem means. It doesn't mean stating a fact
you don't happen to like.
boltar@nowhere.co.uk: Dec 18 04:26PM

On Tue, 17 Dec 2019 08:32:21 -0800 (PST)
 
>"Invalid"/"Incomplete"/"Half-received"/"Erred" states of objects are the common
 
>source of errors. You are rare fan of iostreams failbit-badbit garbage it
>seems?
 
I never use iostreams unless I have no choice. They're just bloat inbetween
my code and the OS I/O system.
 
My point is any class likely to be flung around a program as instances usually
has some kind of flag designating whether an instance is valid. Personally
however I prefer pointers.
 
>> And if you're dealing with pointers just
>> return NULL.
 
>Per-object dynamic memory management is common source of inefficiency.
 
And you think creating an instance of optional for a function return just to
signify a valid return value and then having to call a method to get the actual
contained instance is efficient?
 
 
>Because C++ is often more efficient than alternatives and can union non-pod
>types in variant. If C++ can't do it then there are no chance to do better job
>with your Perl ... or what you program there.
 
I don't use Perl.
 
 
>PODs are useful only for dealing with those low level operations. Most
>embedded controllers have tens of kilobytes of RAM (since it just costs
>nothing) and so are often expected to be quite smart these days.
 
No all of them. Some PICs have < 1K of RAM.
 
Anyway, when someone shows me a sane use case of unionising non POD types
perhaps I'll see variant as something other than just more noise in the C++
spec.
Daniel <danielaparker@gmail.com>: Dec 18 09:36AM -0800

On Monday, December 16, 2019 at 4:00:51 PM UTC-5, David Brown wrote:
 
> gcc supports 128-bit types even with "-std=c11 -pedantic"
 
But no support for <limits>, unless with -std=gnu++11
Daniel <danielaparker@gmail.com>: Dec 18 09:47AM -0800

On Monday, December 16, 2019 at 1:21:40 PM UTC-5, Öö Tiib wrote:
 
> to use reliable union, and optional is a variant between value and
> nothing. So "purist" who can wield such trivial tools typically
> wins such a sorry "latitudinarians" who can't.
 
optional has a pleasing interface, variant (in my opinion :)) less so.
 
I experimented with providing a non-throwing alternative interface with
optional, but value and nothing aren't usually the states that you want,
rather value and error condition.
 
Daniel
Mr Flibble <flibbleREMOVETHISBIT@i42.co.uk>: Dec 18 07:11PM


> And you think creating an instance of optional for a function return just to
> signify a valid return value and then having to call a method to get the actual
> contained instance is efficient?
 
How thick are you? That isn't using optionals properly; you really are clueless.
 
/Flibble
 
--
"Snakes didn't evolve, instead talking snakes with legs changed into snakes." - Rick C. Hodgin
 
"You won't burn in hell. But be nice anyway." – Ricky Gervais
 
"I see Atheists are fighting and killing each other again, over who doesn't believe in any God the most. Oh, no..wait.. that never happens." – Ricky Gervais
 
"Suppose it's all true, and you walk up to the pearly gates, and are confronted by God," Byrne asked on his show The Meaning of Life. "What will Stephen Fry say to him, her, or it?"
"I'd say, bone cancer in children? What's that about?" Fry replied.
"How dare you? How dare you create a world to which there is such misery that is not our fault. It's not right, it's utterly, utterly evil."
"Why should I respect a capricious, mean-minded, stupid God who creates a world that is so full of injustice and pain. That's what I would say."
Daniel <danielaparker@gmail.com>: Dec 18 11:23AM -0800

On Wednesday, December 18, 2019 at 2:12:03 PM UTC-5, Mr Flibble wrote:
> On 18/12/2019 16:26, boltar@nowhere.co.uk wrote:
 
> > And you think creating an instance of optional for a function return just >> to signify a valid return value and then having to call a method to get the >> actual contained instance is efficient?
 
> That isn't using optionals properly
 
You wouldn't use optional for a function return?
 
Daniel
"Öö Tiib" <ootiib@hot.ee>: Dec 18 11:28AM -0800


> My point is any class likely to be flung around a program as instances usually
> has some kind of flag designating whether an instance is valid. Personally
> however I prefer pointers.
 
What is the point to fling that invalid stuff around? That is another
typical performance drain, waste of storage and source of errors.
Pass reference to good stuff if you have it and call overload without
that parameter when you don't have it.
 
 
> And you think creating an instance of optional for a function return just to
> signify a valid return value and then having to call a method to get the actual
> contained instance is efficient?
 
Mr Flibble was correct, it is clueless response. Optional is not good
for that. Prefer exceptions as signals of failures. When failure is
common (and it matters) use std::variant<Value, FailureDetails> as
alternative to exceptions. Optional is good for *storing* values that
may be missing (or acquired lazily when needed) without dynamic memory
management and loss of locality.
 
> >types in variant. If C++ can't do it then there are no chance to do better job
> >with your Perl ... or what you program there.
 
> I don't use Perl.
 
Doesn't matter. You expressed opinion that C++ is wrong tool when
memory space is critical. So I just imagined that maybe some Perl
programmer can say such nonsense.
 
 
> Anyway, when someone shows me a sane use case of unionising non POD types
> perhaps I'll see variant as something other than just more noise in the C++
> spec.
 
Huh? PODs are really only useful for low level operations with data of
precise memory layout. On rest of cases a class with constructors,
destructors, private members, virtual member functions and/or non-POD
data members is more handy. Don't you use classes? Union
of classes can be great performance optimization.
"Öö Tiib" <ootiib@hot.ee>: Dec 18 11:31AM -0800

On Wednesday, 18 December 2019 21:23:49 UTC+2, Daniel wrote:
 
> > > And you think creating an instance of optional for a function return just >> to signify a valid return value and then having to call a method to get the >> actual contained instance is efficient?
 
> > That isn't using optionals properly
 
> You wouldn't use optional for a function return?
 
Only when it is normal that it is missing and then stored as optional.
"Öö Tiib" <ootiib@hot.ee>: Dec 18 11:49AM -0800

On Wednesday, 18 December 2019 19:47:14 UTC+2, Daniel wrote:
 
> I experimented with providing a non-throwing alternative interface with
> optional, but value and nothing aren't usually the states that you want,
> rather value and error condition.
 
Variant of Value,Failure1,Failure2 etc. is better to use as "Fallible".
Mr Flibble <flibbleREMOVETHISBIT@i42.co.uk>: Dec 18 07:56PM

On 18/12/2019 19:23, Daniel wrote:
 
>>> And you think creating an instance of optional for a function return just >> to signify a valid return value and then having to call a method to get the >> actual contained instance is efficient?
 
>> That isn't using optionals properly
 
> You wouldn't use optional for a function return?
 
Ah, I misread what "boltar" said; obviously using them for function return is fine and calling a method to get the contained value is not an issue like "boltar" suggests.
 
/Flibble
 
--
"Snakes didn't evolve, instead talking snakes with legs changed into snakes." - Rick C. Hodgin
 
"You won't burn in hell. But be nice anyway." – Ricky Gervais
 
"I see Atheists are fighting and killing each other again, over who doesn't believe in any God the most. Oh, no..wait.. that never happens." – Ricky Gervais
 
"Suppose it's all true, and you walk up to the pearly gates, and are confronted by God," Byrne asked on his show The Meaning of Life. "What will Stephen Fry say to him, her, or it?"
"I'd say, bone cancer in children? What's that about?" Fry replied.
"How dare you? How dare you create a world to which there is such misery that is not our fault. It's not right, it's utterly, utterly evil."
"Why should I respect a capricious, mean-minded, stupid God who creates a world that is so full of injustice and pain. That's what I would say."
Mr Flibble <flibbleREMOVETHISBIT@i42.co.uk>: Dec 18 08:00PM

On 18/12/2019 19:28, Öö Tiib wrote:
> alternative to exceptions. Optional is good for *storing* values that
> may be missing (or acquired lazily when needed) without dynamic memory
> management and loss of locality.
 
Yes, you shouldn't use empty optionals to indicate an error: use exceptions for that.
 
/Flibble
 
--
"Snakes didn't evolve, instead talking snakes with legs changed into snakes." - Rick C. Hodgin
 
"You won't burn in hell. But be nice anyway." – Ricky Gervais
 
"I see Atheists are fighting and killing each other again, over who doesn't believe in any God the most. Oh, no..wait.. that never happens." – Ricky Gervais
 
"Suppose it's all true, and you walk up to the pearly gates, and are confronted by God," Byrne asked on his show The Meaning of Life. "What will Stephen Fry say to him, her, or it?"
"I'd say, bone cancer in children? What's that about?" Fry replied.
"How dare you? How dare you create a world to which there is such misery that is not our fault. It's not right, it's utterly, utterly evil."
"Why should I respect a capricious, mean-minded, stupid God who creates a world that is so full of injustice and pain. That's what I would say."
Daniel <danielaparker@gmail.com>: Dec 18 12:05PM -0800

On Wednesday, December 18, 2019 at 2:49:37 PM UTC-5, Öö Tiib wrote:
> > optional, but value and nothing aren't usually the states that you want,
> > rather value and error condition.
 
> Variant of Value,Failure1,Failure2 etc. is better to use as "Fallible".
 
I thought you'd want to wrap that, as returning a variant would be an
excruciatingly unfriendly interface, I think you'd want success() and value()
and value_or(), as well as error_code or whatever.
 
Daniel
Paavo Helde <myfirstname@osa.pri.ee>: Dec 18 10:12PM +0200

> Anyway, when someone shows me a sane use case of unionising non POD types
> perhaps I'll see variant as something other than just more noise in the C++
> spec.
 
Use cases for a non-POD type in an union are the same as using a non-POD
type anywhere else, mostly RAII and encapsulation. An alternative (which
was needed before C++11) would be to use POD types in the union and
replicate the RAII and encapsulation in the class wrapping the union,
but this would mean reinventing a lot of wheels and losing modularity.
For example, if one of the union types is smart pointer, one would need
to basically store a raw pointer inside the union and reimplement the
smart pointer functionality inside the wrapper class.
 
A union is just a technical tool for reducing memory usage. An obvious
example is a polymorphic item type in a scripting language interpreter
which could store either single integers or floating-point values, but
at the same time strings (esp. useful with small string optimization),
smartpointers to larger data objects, etc. It would make no sense to use
a 10x larger class than necessary for the most heavily used data
structure in the program.
 
Another technical tool which can be used for reducing such memory usage
is derivation. The Python interpreter (written in C) is basically using
derivation, with every item allocated dynamically, featuring tedious
manual refcounting and multi-stage vtables. This has its own benefits
and drawbacks. Python model uses more memory, more dynamic allocations
and more redirection than a union-based approach would have, but at the
same time it is more readily extendable.
"Öö Tiib" <ootiib@hot.ee>: Dec 18 12:19PM -0800

On Wednesday, 18 December 2019 22:05:18 UTC+2, Daniel wrote:
 
> I thought you'd want to wrap that, as returning a variant would be an
> excruciatingly unfriendly interface, I think you'd want success() and value()
> and value_or(), as well as error_code or whatever.
 
Sure. That is great thing about C++. Convenience wrappers do not cause
any performance losses and there are templates to automate making such
convenience wrappers.
Thiago Adams <thiago.adams@gmail.com>: Dec 18 11:04AM -0800

Who likes the design of std::chrono?
For me, std::chrono is a sample of over-engineering
and too abstractions.
 
And it is becoming even more complex in C++ 20.
E.g
https://en.cppreference.com/w/cpp/chrono/month_day
"Öö Tiib" <ootiib@hot.ee>: Dec 18 12:11PM -0800

On Wednesday, 18 December 2019 21:05:00 UTC+2, Thiago Adams wrote:
 
> And it is becoming even more complex in C++ 20.
> E.g
> https://en.cppreference.com/w/cpp/chrono/month_day
 
Gregorian calendar is a total mess. Few on this planet have implemented
it properly down to single second. Additionally the local time in it is
political decision that changes from year to year. So one needs database
to find out what wall clock did show at time of certain event few
years ago. I guess Boost.Date_Time for example is still defective. It
sure was when I last tried it out of boredom.
 
The chrono just tries to make Gregorian calendar a bit less pain to
use but grisly aspects of it are still there. Also it likely does
not link stuff that you don't use into your program (unlike
Boost.Date_Time did).
Bonita Montero <Bonita.Montero@gmail.com>: Dec 18 04:07PM +0100

... could make std::hardware_destructive_interference_size
and std::hardware_constructive_interference_size different?
You received this digest because you're subscribed to updates for this group. You can change your settings on the group membership page.
To unsubscribe from this group and stop receiving emails from it send an email to comp.lang.c+++unsubscribe@googlegroups.com.

No comments: