Compare commits

..

11 commits

Author SHA1 Message Date
f23dbe1986 Parameters: streamline automatic type conversion
Can now express the automatic conversion between all allowed `BaseTypes`
by invoking the `TypeHandler` interface directly. The interfaces were streamlined
and storage size is managed automatically at compile time.
2026-09-03 01:42:18 +02:00
b80587fd1b Parameters: setup bit-layout for ID-Record 2026-09-03 00:18:46 +02:00
ee629b56b7 Parameter: resolve PolymorpicValue setup
`PolymorphicValue` incurs some quite confusing requirements due to
the clumsy way how the instance handling and copy support must be injected.
As pointed out in #1197, with modern C++, this could be much simplified.

An overhaul of `PolymorphicValue` seems urgent thus -- in the meanwhile
we need to introduce more flexibiltiy with base-class template parameters,
so that we can inject the CopySupport interface at usage site of the
complete implementation class chain. Furthermore, the size of the VTable
is added automatically to the storage requirements in `PolymorphicValue`,
so we must subtract it when specifying the payload size by a compile-time
expression based on `sizeof(ParamData<double>)`

With these tweaks, we can now keep the limit of 4 «slots» (32 bytes)
and still reserve 64bit for ID and type flags.
2026-09-03 00:10:37 +02:00
3d01ebf63c Parameter: introduce ID-Record into the impl-interface
The solution from yesterday works, but is needlessly indirect.
However, if we want to circumvent ''any indirection'' in the
simple standard case, then it turns out to be necessary to
have some kind of ''flag store'' already in the `Disposition`
(the implementation service interface). Because otherwise
it would be impossible to trigger the short-circuit access
without going through some kind of indirection.

Need to define a generic ID-Record with some flexible extension space
that can be used by subclasses; and notably we need to generate some
base-type-IDs on a static level -- which should be possible, since all
allowed BaseTypes are defined as Type-Sequence.
2026-09-03 00:02:16 +02:00
f2244414aa Parameter: simple testcase PASS (see #1431)
Add value access implementation of the Provision interface
by direct cast and access to the embedded value in `ParamData<VAL>`;
obviously this is an indirect dispatch, based on the actual type `VAL`

The test demonstrates the basic machinery built thus far
 - have an embedded container with inline storage
 - dispatch using type information encoded into the VTable
2026-09-02 01:48:51 +02:00
2467405c25 Parameter: first rough-edged implementation of value access
...as expected, the first attempt to walk the full access path
unveils a host of problematic aspects in the design...
2026-09-02 01:27:27 +02:00
a5f1709bff Parameter: allow to pass an initial parameter value
...and in addition check that the defined value type
is consistent with the list of pre-configured `BaseTypes`

Signed-off-by: Ichthyostega <prg@ichthyostega.de>
2026-09-02 01:19:24 +02:00
8be0a076c7 Parameter: build container with in-place init
turns out to be quite tricky, due to the overly convoluted implementation
of PolymorphicValue (which looks quite dated, generally speaking,
and could use a complete overhaul).

- pass the basic value type as template parameter through the Builder
- allow for the ability to define an initial value for the parameter
- invoke the protected constructor of PolymorphicValue, directly passing
  a ''type tag'' to specify the implementation data package to be placed
  into the embedded data buffer
2026-09-02 01:19:24 +02:00
80944ab956 Parameter: now able to define the complete implementation layout
- `Disposition` is the service-API used by the front-End container
 - `ParamData<TY>` is a complete implementation with a inline-value buffer
 - The front-End is based on the `PolymorphicValue` container from our support-Lib
2026-09-01 23:15:09 +02:00
f452cd268d Parameters: establish layered implementation order
Finally able to settle upon a layering for the implementation facilities

 Provision:: represents the core idea of a parameter
 Domain:: assumes the ability to handle typed values
 Disposition:: complete implementation capabilities

 BaseDomain:: establish type conversion functionality
 TypedEntity:: provide a type and ID descriptor and scale configuration
 ParamData:: full implementation based on an embedded value buffer
2026-09-01 22:55:56 +02:00
0ebb2afc15 Parameters: reorganise TypeHandler interface
The original design (based on Alexandrescu) is more elegant,
but has the downside to bloat the VTable size due to the mix-in
arrangement used to generate the interface.

The ongoing design has revealed a tight constraint on element size
for the parameters; thus the change to a linearised inheritance chain.

The overall purpose remains the same: the ability to generate a
double-dispatch type conversion, so that the actual value type of the
parameter can be treated as an implicit implementation detail.
2026-09-01 20:46:40 +02:00
13 changed files with 1135 additions and 302 deletions

View file

@ -115,6 +115,26 @@ namespace meta {
{ };
/**
* Metafunction: build an ID-Type based on the position in the list
* @remark when the type is not in the list, TypeIdxID ≔ 0
*/
template<typename TY, typename TYPES, uint idx=1>
struct TypeIdxID
: std::integral_constant<uint, 0>
{ };
template<typename TY, typename TYPES, uint idx>
struct TypeIdxID<TY, Node<TY,TYPES>, idx> ///< @return 1-based position in case of match
: std::integral_constant<uint, idx>
{ };
template<typename X, typename TY, typename TYPES, uint idx>
struct TypeIdxID<X, Node<TY,TYPES>, idx> ///< else recurse to check next element
: TypeIdxID<X, TYPES, idx+1>
{ };
/**
* Build a list of const types from a given typelist.

View file

@ -26,6 +26,7 @@
#define LIB_PAR_DISPOSITION_H
#include "lib/par/spec.hpp"
#include "lib/par/provision.hpp"
#include "lib/par/param-type.hpp"
@ -33,6 +34,31 @@
namespace lib {
namespace par {
using ValStorage = ValBuffStorage<BASETYPE_MAX_SIZ>;
/**
* Implementation-Service: complete Parameter functionality.
* Includes the ability to access / set a »value«, attach automation,
* identify and convert underlying value data types and handle
* trait- and identity tags and the specifics of the value scale.
*/
class Disposition
: public Domain
{
IDRecord idr_;
public:
template<typename X>
X extract() const;
template<typename X>
void setVal (X);
private:
template<typename X>
bool isBaseDomainMatch() const;
};
/**
@ -40,12 +66,88 @@ namespace par {
* with domain and scale, and a value provision. Can be generated through a builder
* notation and stored within the Parameter object (as a container).
*/
class Disposition
: public ParamType
template<typename VAL, class IFA =Disposition> /////////////////////////////////////////////////////TICKET #1197 : the second template argument is quite confusing and became necessary due to the limitations of PolymorphicValue
class ParamData
: public TypedEntity<VAL, IFA>
{
VAL val_;
Provision* src_;
/* === Provision Interface === */
void retrieveInto (ValBuff&) const override;
void setValFrom (ValBuff const&) override;
public:
ParamData (VAL initVal)
: val_{std::move (initVal)}
, src_{nullptr}
{ }
};
template<typename X>
using FullDomain = BaseDomain<X, Disposition>;
template<typename VAL, class IFA>
void
ParamData<VAL, IFA>::retrieveInto (ValBuff& target) const
{
asValue<VAL>(target) = val_;
}
template<typename VAL, class IFA>
void
ParamData<VAL, IFA>::setValFrom (ValBuff const& newVal)
{
val_ = asValue<VAL>(newVal);
}
template<typename X>
X
Disposition::extract() const
{
X result; // RVO
if (isBaseDomainMatch<X>())
{ // short-circuit by direct force-cast
retrieveInto (asValBuff (result));
}
else
{ // run full type-conversion dispatch
ValStorage valueBuffer;
this->retrieveInto (valueBuffer);
this->extractAs (result, valueBuffer);
}
return result;
}
template<typename X>
void
Disposition::setVal (X changedVal)
{
if (isBaseDomainMatch<X>())
{ // short-circuit by direct force-cast
setValFrom (asValBuff (changedVal));
}
else
{ // run full type-conversion dispatch
ValStorage valueBuffer;
this->conform (valueBuffer, changedVal);
this->setValFrom (valueBuffer);
}
}
template<typename X>
bool
Disposition::isBaseDomainMatch() const
{
return false; /////////////////////////OOO running into a dead end here? how can we possibly access a type tag marker without indirection??
}
}} // namespace lib::par

View file

@ -34,8 +34,8 @@
#define LIB_PAR_DOMAIN_H
#include "lib/par/spec.hpp"
#include "lib/meta/typelist.hpp"
//#include "lib/meta/typelist-util.hpp"
#include "lib/meta/generator.hpp"
#include "lib/par/provision.hpp"
#include "lib/meta/trait.hpp"
@ -54,62 +54,31 @@ namespace par {
using std::numeric_limits;
/* ===== Type Handler Interface for generic parameter value access ===== */
template<typename X>
constexpr inline ValBuff&
asValBuff (X& something)
{
void* rawMem{& something};
return * static_cast<ValBuff*> (rawMem);
}
template<typename X>
constexpr inline ValBuff const&
asValBuff (X const& something)
{
void const * rawMem{& something};
return * static_cast<ValBuff const *> (rawMem);
}
template<typename X>
constexpr inline X&
asValue (ValBuff& storage)
{
void* rawMem{& storage};
return * static_cast<X*> (rawMem);
}
template<typename X>
constexpr inline X const&
asValue (ValBuff const& storage)
{
void const * rawMem{& storage};
return * static_cast<X const *> (rawMem);
}
template<typename X>
class TypeHandler
class HandlerBase
: public Provision
{
public:
virtual void extractAs (X& targetVal, ValBuff const& valBuff) =0;
virtual void conform (ValBuff& targetBuff, X const& srcVal) =0;
public:
void extractAs();
void conform();
};
// using lib::meta::typeseq;
template<typename X, class PAR>
class TypeHandler
: public PAR
{
public:
virtual void extractAs (X& targetVal, ValBuff const& valBuff) const =0;
virtual void conform (ValBuff& targetBuff, X const& srcVal) =0;
using PAR::extractAs;
using PAR::conform;
};
using BaseTypes = meta::Types<int
,int64_t
,uint
,uint64_t
,double
,float
,bool
>;
/** build a generic visitor interface for all types in list */
using TypeHandlerInterface = meta::InstantiateForEach<BaseTypes::List, TypeHandler, Provision>;
using TypeHandlerInterface = meta::InstantiateChained<BaseTypes::List, TypeHandler, HandlerBase>;
/**
@ -129,185 +98,12 @@ namespace par {
virtual ~Domain(); ///< this is an interface
virtual void applyLimit (ValBuff&) =0;
virtual void transferTo (ValBuff const& source, Domain& targetDomain, ValBuff& target) =0;
virtual void transferTo (ValBuff const& source, Domain& targetDomain, ValBuff& target) const =0;
protected:
};
// GCC > 13 warns at class definition when a new overload shadows an inherited virtual function.
// While theoretically correct, in practice any call will be dispatched through the base interface,
// which in turn is also generated by metaprogramming from a type list.
// See https://gcc.gnu.org/bugzilla/show_bug.cgi?id=109740
_Pragma("GCC diagnostic push") \
_Pragma("GCC diagnostic ignored \"-Woverloaded-virtual\"")
template<typename V>
struct DomainSetup
{
template<typename X, class BAS>
class TypeHandlerImpl
: public BAS
{
void extractAs (X& targetVal, ValBuff const& valBuff) override;
void conform (ValBuff& targetBuff, X const& srcVal) override;
};
using TypeHandlerChain = meta::InstantiateChained<BaseTypes::List, TypeHandlerImpl, Domain>;
};
template<typename V>
class BaseDomain
: public DomainSetup<V>::TypeHandlerChain
{
public:
void applyLimit (ValBuff&) override;
void transferTo (ValBuff const& source, Domain& targetDomain, ValBuff& target) override;
};
/* ===== type conversion details ===== */
/** Constraint: type \a SUB can not represent the full domain of type \a BAS
* @todo implicitly also implements a limitation to »numeric« types,
* due to the use of std::numeric_limits
*/
template<typename SUB, typename BAS>
concept sub_domain = std::signed_integral<SUB> != std::signed_integral<BAS>
or std::numeric_limits<SUB>::max() < std::numeric_limits<BAS>::max()
or std::numeric_limits<SUB>::lowest() > std::numeric_limits<BAS>::lowest()
;
_Pragma("GCC diagnostic push") \
_Pragma("GCC diagnostic ignored \"-Wsign-compare\"")
// the following functions are specifically crafted to work around
// the ambiguities caused by automatic signed-to-unsigned promotion;
// furthermore, the automatic promotion allows to perform the comparison.
template<typename X, typename Y>
inline constexpr bool
isLower_safe (X const& x, Y const& y)
{
return isNeg(x) == isNeg(y)? x < y
: isNeg(x);
}
template<typename X, typename Y>
inline constexpr bool
isLarger_safe (X const& x, Y const& y)
{
return isNeg(x) == isNeg(y)? x > y
: isNeg(y);
}
_Pragma("GCC diagnostic pop")
/** generic helper to conform into a common value domain
* @tparam SUB the implied target value domain
* @tparam BAS source data type
* @return a value in source data type,
* yet conformed into the target data range
*/
template<typename SUB, typename BAS>
inline constexpr BAS
preClamp (BAS const& value)
{
return value;
}
/** special case: clamp the source value into the target value domain.
* @remark tricky due to automatic conversions between signed/unsigned */
template<typename SUB, typename BAS> requires (sub_domain<SUB,BAS>
and not same_as<SUB,bool>)
inline constexpr BAS
preClamp (BAS const& rawVal)
{
static_assert (std::is_constructible_v<BAS,SUB const&>
,"Value domains must overlap at least partially "
"and values must be cross-constructible within overlap");
auto upperBound = numeric_limits<SUB>::max();
auto lowerBound = numeric_limits<SUB>::lowest();
return isLarger_safe(rawVal, upperBound)? BAS(upperBound)
: isLower_safe (rawVal, lowerBound)? BAS(lowerBound)
: rawVal;
}
/** special case: trigger a bool at the 0.5 level */
template<same_as<bool> B, floating_point F>
inline constexpr F
preClamp (F const& rawVal)
{
return 0.5 < rawVal? F{1} : F{0};
}
template<typename V, typename X>
inline void
assignConverted (V& targetVal, X const& srcVal)
{
if constexpr (std::is_assignable_v<V&, X const&>)
{
targetVal = preClamp<V> (srcVal);
}
else
if constexpr (std::is_constructible_v<V, X const&>)
{
targetVal.~U();
new(&targetVal) V (preClamp<V> (srcVal));
}
else
static_assert (!sizeof(X), "this type conversion is not supported");
}
template<typename V>
template<typename X, class BAS>
inline void
DomainSetup<V>::TypeHandlerImpl<X,BAS>::extractAs (X& targetVal, ValBuff const& valBuff)
{
V const& srcVal = asValue<V> (valBuff);
assignConverted (targetVal, srcVal);
}
template<typename V>
template<typename X, class BAS>
inline void
DomainSetup<V>::TypeHandlerImpl<X,BAS>::conform (ValBuff& targetBuff, X const& srcVal)
{
V& targetVal = asValue<V> (targetBuff);
assignConverted (targetVal, srcVal);
}
template<typename V>
inline void
BaseDomain<V>::applyLimit (ValBuff& valBuff)
{
V& val{asValue<V> (valBuff)};
val = preClamp<V> (val);
}
template<typename V>
inline void
BaseDomain<V>::transferTo (ValBuff const& source, Domain& targetDomain, ValBuff& target)
{
TypeHandler<V>& typeHandler{targetDomain};
typeHandler.conform (target, asValue<V> (source));
targetDomain.applyLimit (target);
}
}} // namespace lib::par
#endif /*LIB_PAR_DOMAIN_H*/

View file

@ -14,8 +14,17 @@
/** @file param-type.hpp
** Specification of the value domain and scale of a parameter.
** A ParamType descriptor implicitly also encodes the concrete value type, the
** allowed value range, clipping behaviour and specifics of the scale (discrete,
** The implementation of parameters is built up in layers, starting from the generic
** interfaces \ref Provision, which describes the fundamental capabilities of a
** parameter as conceptualised here) and \ref Domain to support type conversions.
**
** All extensions beyond this point can be considered implementation-level services.
** The BaseDomain layer provides the actual type conversion services, based on internal
** knowledge of the concrete data type handled by this parameter.
**
** A \ref TypedEntity descriptor adds storage to capture type properties and allow
** for an ID registration. In addition, the concrete value type is tagged, marking
** the allowed value range, clipping behaviour and specifics of the scale (discrete,
** stepping, continuous, logarithmic...).
**
** @todo WIP-WIP-WIP can be considered an initial draft and placeholder, as of 2026
@ -27,22 +36,197 @@
#include "lib/par/domain.hpp"
#include "lib/meta/generator.hpp"
namespace lib {
namespace par {
// GCC > 13 warns at class definition when a new overload shadows an inherited virtual function.
// While theoretically correct, in practice any call will be dispatched through the base interface,
// which in turn is also generated by metaprogramming from a type list.
// See https://gcc.gnu.org/bugzilla/show_bug.cgi?id=109740
_Pragma("GCC diagnostic push") \
_Pragma("GCC diagnostic ignored \"-Woverloaded-virtual\"")
template<typename VAL, class IFA>
struct DomainSetup
{
template<typename X, class PAR>
class TypeHandlerImpl
: public PAR
{
void extractAs (X& targetVal, ValBuff const& valBuff) const override;
void conform (ValBuff& targetBuff, X const& srcVal) override;
};
using TypeHandlerChain = meta::InstantiateChained<BaseTypes::List, TypeHandlerImpl, IFA>;
};
template<typename VAL, class IFA>
class BaseDomain
: public DomainSetup<VAL, IFA>::TypeHandlerChain
{
public:
void applyLimit (ValBuff&) override;
void transferTo (ValBuff const& source, Domain& targetDomain, ValBuff& target) const override;
};
/* ===== type conversion details ===== */
/** Constraint: type \a SUB can not represent the full domain of type \a BAS
* @todo implicitly also implements a limitation to »numeric« types,
* due to the use of std::numeric_limits
*/
template<typename SUB, typename BAS>
concept sub_domain = std::signed_integral<SUB> != std::signed_integral<BAS>
or std::numeric_limits<SUB>::max() < std::numeric_limits<BAS>::max()
or std::numeric_limits<SUB>::lowest() > std::numeric_limits<BAS>::lowest()
;
_Pragma("GCC diagnostic push") \
_Pragma("GCC diagnostic ignored \"-Wsign-compare\"")
// the following functions are specifically crafted to work around
// the ambiguities caused by automatic signed-to-unsigned promotion;
// furthermore, the automatic promotion allows to perform the comparison.
template<typename X, typename Y>
inline constexpr bool
isLower_safe (X const& x, Y const& y)
{
return isNeg(x) == isNeg(y)? x < y
: isNeg(x);
}
template<typename X, typename Y>
inline constexpr bool
isLarger_safe (X const& x, Y const& y)
{
return isNeg(x) == isNeg(y)? x > y
: isNeg(y);
}
_Pragma("GCC diagnostic pop")
/** generic helper to conform into a common value domain
* @tparam SUB the implied target value domain
* @tparam BAS source data type
* @return a value in source data type,
* yet conformed into the target data range
*/
template<typename SUB, typename BAS>
inline constexpr BAS
preClamp (BAS const& value)
{
return value;
}
/** special case: clamp the source value into the target value domain.
* @remark tricky due to automatic conversions between signed/unsigned */
template<typename SUB, typename BAS> requires (sub_domain<SUB,BAS>
and not same_as<SUB,bool>)
inline constexpr BAS
preClamp (BAS const& rawVal)
{
static_assert (std::is_constructible_v<BAS,SUB const&>
,"Value domains must overlap at least partially "
"and values must be cross-constructible within overlap");
auto upperBound = numeric_limits<SUB>::max();
auto lowerBound = numeric_limits<SUB>::lowest();
return isLarger_safe(rawVal, upperBound)? BAS(upperBound)
: isLower_safe (rawVal, lowerBound)? BAS(lowerBound)
: rawVal;
}
/** special case: trigger a bool at the 0.5 level */
template<same_as<bool> B, floating_point F>
inline constexpr F
preClamp (F const& rawVal)
{
return 0.5 < rawVal? F{1} : F{0};
}
template<typename V, typename X>
inline void
assignConverted (V& targetVal, X const& srcVal)
{
if constexpr (std::is_assignable_v<V&, X const&>)
{
targetVal = preClamp<V> (srcVal);
}
else
if constexpr (std::is_constructible_v<V, X const&>)
{
targetVal.~U();
new(&targetVal) V (preClamp<V> (srcVal));
}
else
static_assert (!sizeof(X), "this type conversion is not supported");
}
template<typename VAL, class IFA>
template<typename X, class PAR>
inline void
DomainSetup<VAL,IFA>::TypeHandlerImpl<X,PAR>::extractAs (X& targetVal, ValBuff const& valBuff) const
{
VAL const& srcVal = asValue<VAL> (valBuff);
assignConverted (targetVal, srcVal);
}
template<typename VAL, class IFA>
template<typename X, class PAR>
inline void
DomainSetup<VAL,IFA>::TypeHandlerImpl<X,PAR>::conform (ValBuff& targetBuff, X const& srcVal)
{
VAL& targetVal = asValue<VAL> (targetBuff);
assignConverted (targetVal, srcVal);
}
template<typename VAL, class IFA>
inline void
BaseDomain<VAL,IFA>::applyLimit (ValBuff& valBuff)
{
VAL& val{asValue<VAL> (valBuff)};
val = preClamp<VAL> (val);
}
template<typename VAL, class IFA>
inline void
BaseDomain<VAL,IFA>::transferTo (ValBuff const& source, Domain& targetDomain, ValBuff& target) const
{
targetDomain.conform (target, asValue<VAL> (source));
targetDomain.applyLimit (target);
}
/**
* Interface: represent a specific configuration of parameter value type,
* Service-Interface: represent a specific configuration of parameter value type,
* range and scale. Every ParamType descriptor is also a _prototype_ and has
* an unique identity, ensured by registration, so that it acts as a type identifier.
* @todo RLY? registration??
* Furthermore, the interface exposes allowed conversion and conforming operations.
*/
class ParamType
: public Domain
template<typename VAL, class IFA>
class TypedEntity
: public BaseDomain<VAL,IFA>
{
public:
};

View file

@ -29,11 +29,25 @@
#define LIB_PAR_PARAMETER_H
#include "lib/par/disposition.hpp"
#include "lib/polymorphic-value.hpp"
#include "lib/util.hpp"
#include <utility>
namespace lib {
namespace par {
namespace {
static constexpr size_t PAYLOAD_SIZ = sizeof(ParamData<double>) - sizeof(void*); ////////////////////////TICKET #1197 : this is a mess! PolymorphicValue adds the ADMIN_OVERHEAD (but our payload has already a VTable)
using ParameterImplAPI = Disposition;
using CopySupportMarker = polyvalue::CopySupport<ParameterImplAPI>;
using ParamContainer = PolymorphicValue<ParameterImplAPI, PAYLOAD_SIZ, CopySupportMarker>;
}
using util::unConst;
/**
@ -41,12 +55,14 @@ namespace par {
* The value can be fixed or supplied by an automation function.
*/
class Parameter
: protected ParamContainer
{
public:
template<typename VAL>
class Builder;
template<typename VAL>
VAL getVal();
VAL getVal() const;
template<typename VAL>
void setVal (VAL&&);
@ -54,37 +70,59 @@ namespace par {
/* === Builder API === */
template<typename VAL>
static Builder forType();
static Builder<VAL>
forType() { return {}; }
template<typename VAL>
static Builder<std::decay_t<VAL>>
forValue (VAL&& initVal)
{
using PayloadType = std::decay_t<VAL>;
return forType<PayloadType>()
.withValue (std::forward<VAL> (initVal));
}
protected:
template<class IMP, typename...ARGS>
Parameter (IMP* typeTag, ARGS&&... args)
: PolymorphicValue (typeTag, std::forward<ARGS>(args)...)
{ }
};
template<typename VAL> requires par_basetype<VAL>
class Parameter::Builder
{
VAL initVal_{};
public:
Parameter
build()
{
UNIMPLEMENTED ("terminal builder operation: package a disposition into the Parameter");
using ImplPackage = ParamData<VAL, CopySupportMarker>; //////////////////////////////////////////TICKET #1197 : remove the necessity to inject the CopySupportMarker
ImplPackage* typeTag{nullptr};
Parameter resParam{typeTag, std::move (initVal_)};
return resParam;
}
template<typename X>
Builder&&
withValue (X&& initVal)
{
initVal_ = std::forward<X> (initVal);
return std::move(this);
}
};
template<typename VAL>
Parameter::Builder
Parameter::forType()
{
UNIMPLEMENTED ("how to setup the base type configuration? do we need a type parameter in the Builder class?");
}
template<typename VAL>
VAL
Parameter::getVal()
Parameter::getVal() const
{
UNIMPLEMENTED ("extract the »value«, possibly applying suitable type conversions");
static_assert (isBaseType<VAL>, "only preconfigured parameter BaseTypes are supported");
return unConst(this)->getPayload().extract<VAL>();
}
@ -92,7 +130,9 @@ namespace par {
void
Parameter::setVal (VAL&& changedVal)
{
UNIMPLEMENTED ("apply suitable type conversions and clamping, then transfer the new value into the Provision interface");
static_assert (isBaseType<VAL>, "only preconfigured parameter BaseTypes are supported");
getPayload().setVal (changedVal);
}

View file

@ -33,16 +33,62 @@ namespace par {
using time::Time;
/** Marker for an opaque value buffer with
* undisclosed size and content type */
struct ValBuff { /*placeholder*/ };
template<typename X>
constexpr inline ValBuff&
asValBuff (X& something)
{
void* rawMem{& something};
return * static_cast<ValBuff*> (rawMem);
}
template<typename X>
constexpr inline ValBuff const&
asValBuff (X const& something)
{
void const * rawMem{& something};
return * static_cast<ValBuff const *> (rawMem);
}
template<typename X>
constexpr inline X&
asValue (ValBuff& storage)
{
void* rawMem{& storage};
return * static_cast<X*> (rawMem);
}
template<typename X>
constexpr inline X const&
asValue (ValBuff const& storage)
{
void const * rawMem{& storage};
return * static_cast<X const *> (rawMem);
}
template<size_t bytes>
struct ValBuffStorage
: ValBuff
{
std::byte data[bytes];
};
/**
* Interface: access to a parameter's value, to adjust or evaluate automation.
* Conceptually, the value is decomposed into a _base value_ and possibly a
* time-controlled adjustment (automation). The base value can be retrieved
* and assigned, while the current time-based value is the result of evaluation.
* Any parameter value is associated to a ParamType that defines the underlying
* value domain and possibly a scale with range limits and metric constraints.
* Any parameter value is implicitly associated with a Type that defines the
* underlying [value domain](\ref Domain) and possibly a \ref Scale that
* defines range limits and metric constraints.
* @remark the value access and manipulation works _backwards_ from an implicit
* value that is conceptually located _within_ this provision towards
* an ValBuff for external access. The reason for this indirect

95
src/lib/par/spec.hpp Normal file
View file

@ -0,0 +1,95 @@
/*
SPEC.hpp - parameter trait specification
Copyright (C)
2026 Hermann Vosseler <Ichthyostega@web.de>
  **Lumiera** 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 2 of the License, or (at your
  option) any later version. See the file COPYING for further details.
*/
/** @file spec.hpp
** Common definition and specification record for parameters.
** While most functionality of parameters is indirected in some way, allowing
** for future extension, some basic traits are marked as flag, so that frequently
** used code-paths might take a shortcut. Notably the disposition interface, which
** describes the full implementation service of a parameter container, explicitly
** reserves one «slot» of storage for flags, type markers and an ID record.
**
** @todo WIP-WIP-WIP can be considered an initial draft and placeholder, as of 2026
*/
#ifndef LIB_PAR_SPEC_H
#define LIB_PAR_SPEC_H
#include "lib/symbol.hpp"
#include "lib/meta/typelist.hpp"
#include "lib/meta/typelist-util.hpp"
namespace lib {
namespace par {
/**
* Fixed collection of elementary types supported in parameters
*/
using BaseTypes = meta::Types<int
,int64_t
,uint
,uint64_t
,double
,float
,bool
>;
static constexpr uint BASETYPE_CNT = meta::count<BaseTypes::List>();
static constexpr uint BASETYPE_MAX_SIZ = meta::maxSize<BaseTypes::List>();
template<typename T>
static constexpr bool isBaseType = meta::isInList<T, BaseTypes::List>::value;
/** @note Only some fixed base data types are supported as Parameter value type. */
template<typename T>
concept par_basetype = isBaseType<T>;
template<typename T>
using BaseTypeID = meta::TypeIdxID<T, BaseTypes::List>;
/* ===== setup of ID space ===== */
namespace {
auto _bit_fit = [](uint bits){ return (1u << bits) - 1; };
}
static constexpr uint _BASE_TYPE_BITS = 4;
static constexpr uint _SCALES_BITS = 10;
static constexpr uint _PARAM_ID_BITS = 18;
static constexpr uint MAX_BASETYPES = _bit_fit(_BASE_TYPE_BITS); ///< max number of parameter base types that can be configured
static constexpr uint MAX_SCALES = _bit_fit(_SCALES_BITS); ///< max number of distinct scales that can be defined at runtime
static constexpr uint MAX_PARAM_ID = _bit_fit(_PARAM_ID_BITS); ///< max number of distinct param identities that can be created
static_assert (BASETYPE_CNT <= MAX_BASETYPES);
struct IDRecord
{
uint baseTypeID :_BASE_TYPE_BITS = 0;
uint scaleID :_SCALES_BITS = 0;
uint paramIDID :_PARAM_ID_BITS = 0;
};
}} // namespace lib::par
#endif /*LIB_PAR_SPEC_H*/

View file

@ -516,7 +516,7 @@ namespace lib {
static PolymorphicValue
build (ARGS&&... args)
{
Adapter<IMP>* type_to_build_in_buffer(0);
IMP* type_to_build_in_buffer{};
return PolymorphicValue (type_to_build_in_buffer, std::forward<ARGS>(args)...);
}

View file

@ -171,7 +171,7 @@ namespace util {
* @todo 3/2024 seems we have solved this problem several times meanwhile /////////////////////////////////TICKET #1360 sort out floating-point rounding and precision
*/
inline constexpr bool
almostEqual (double d1, double d2, unsigned int ulp =2) noexcept
almostEqual (double d1, double d2, uint ulp =2) noexcept
{
using std::fabs;
return fabs (d1-d2) < DBL_EPSILON * fabs (d1+d2) * ulp
@ -224,6 +224,10 @@ namespace util {
return logB;
}
static_assert (-1 == ilog2(-5));
static_assert ( 0 == ilog2( 1));
static_assert ( 5 == ilog2(42));
} // namespace util
#endif /*UTIL_QUANT_H*/

View file

@ -2,7 +2,7 @@ TESTING "Library Test Suite: parameters" ./test-suite --group=param
PLANNED "Parameter Values" Parameter_test <<END
TEST "Parameter Values" Parameter_test <<END
return: 0
END

View file

@ -19,6 +19,7 @@
#include "test/run.hpp"
//#include "test/test-helper.hpp"
#include "lib/par/domain.hpp"
#include "lib/par/param-type.hpp"
#include "test/diagnostic-output.hpp"////////////TODO
//#include <utility>
@ -168,6 +169,9 @@ namespace test{
template<typename X>
using FullDomain = BaseDomain<X, Domain>;
/** @test base function to access the contents of an opaque buffer
* with known type, and convert into another target type.
* - the base interface #Domain represents an opaque type
@ -183,8 +187,10 @@ namespace test{
void
verify_valueAccess()
{
BaseDomain<int> domInt;
SHOW_EXPR(sizeof(BaseDomain<int>)) ///////////////////////////////////////TODO this should be only one »slot«, but is actually quite large, due to using multiple inheritance in the Domain interface. /////OOO fix that!
FullDomain<int> domInt;
CHECK (sizeof(FullDomain<int>) <= sizeof(void*)); // only the VTable
// use the generic interface for access...
Domain& dom{domInt};
int val = 1 + rani (1000);
@ -193,21 +199,18 @@ SHOW_EXPR(sizeof(BaseDomain<int>)) ///////////////////////////////////////TODO t
uint target1{0};
CHECK (not target1);
TypeHandler<uint>& hu{dom};
hu.extractAs (target1, src);
dom.extractAs (target1, src);
CHECK (target1 == uint(val));
float target2{0};
TypeHandler<float>& hf{dom};
hf.extractAs (target2, src);
dom.extractAs (target2, src);
CHECK (target2 == float(val));
// value clamped to target domain...
val = _MIN<int>;
uint64_t target3{55};
TypeHandler<uint64_t>& hu64{dom};
hu64.extractAs (target3, src);
dom.extractAs (target3, src);
CHECK (target3 == _MIN<uint64_t>);
}
@ -222,27 +225,24 @@ SHOW_EXPR(sizeof(BaseDomain<int>)) ///////////////////////////////////////TODO t
void
verify_valueSetting()
{
BaseDomain<int> domInt;
FullDomain<int> domInt;
Domain& dom{domInt};
int val_in_buff = 0;
ValBuff& target = asValBuff (val_in_buff);
uint src1 = 1 + rani (1000);
TypeHandler<uint>& hu{dom};
hu.conform (target, src1);
dom.conform (target, src1);
CHECK (val_in_buff == int(src1));
double src2 = ranRange (1,100);
CHECK (1 <= src2 and src2 < 100);
TypeHandler<double>& hd{dom};
hd.conform (target, src2);
dom.conform (target, src2);
CHECK (val_in_buff == int(floor (src2)));
// value clamped to target domain...
auto mini = _MIN<int64_t>;
TypeHandler<int64_t>& h64{dom};
h64.conform (target, mini);
dom.conform (target, mini);
CHECK (val_in_buff == _MIN<int>);
}
@ -263,9 +263,9 @@ SHOW_EXPR(sizeof(BaseDomain<int>)) ///////////////////////////////////////TODO t
int64_t i64_val{0};
bool boo{false};
BaseDomain<double> ddom;
BaseDomain<int64_t> idom;
BaseDomain<bool> bdom;
FullDomain<double> ddom;
FullDomain<int64_t> idom;
FullDomain<bool> bdom;
Domain& d1{ddom};
Domain& d3{bdom};

View file

@ -20,6 +20,7 @@
//#include "test/test-helper.hpp"
#include "lib/par/parameter.hpp"
//#include "lib/format-cout.hpp"
#include "test/diagnostic-output.hpp"/////////////TODO
//#include <utility>
//#include <string>
@ -76,6 +77,9 @@ namespace test{
void
simpleUsage()
{
CHECK (sizeof(Parameter) <= 4 * sizeof(void*));
CHECK (BASETYPE_MAX_SIZ <= sizeof(ValStorage));
Parameter par = Parameter::forType<int>().build();
CHECK (0 == par.getVal<int>());

View file

@ -61468,6 +61468,20 @@
</html></richcontent>
</node>
</node>
<node CREATED="1788380815777" ID="ID_339381268" MODIFIED="1788380998740" TEXT="Typlisten-Hilfsmittel">
<node BACKGROUND_COLOR="#d2beaf" COLOR="#5c4d6e" CREATED="1788380823618" ID="ID_763137476" MODIFIED="1788380836976" TEXT="geh&#xf6;rt l&#xe4;ngerfristig etwas konsolidiert...">
<icon BUILTIN="hourglass"/>
</node>
<node CREATED="1788380842279" ID="ID_1993085663" MODIFIED="1788380927706" TEXT="Typlisten und Typ-Sequenzen sind nun voll ineinander &#xfc;berf&#xfc;hrbar">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
<p>
Das Bindeglied steckt in typeseq-util.hpp &#10230; es wurde einfach m&#246;glich durch die Umstellung auf variadische Typ-Sequenzen (beim &#220;bergang auf C++20)
</p>
</body>
</html></richcontent>
</node>
<node CREATED="1540682674455" ID="ID_1625152878" MODIFIED="1557498707236" TEXT="Typliste filtern">
<node CREATED="1540682680286" ID="ID_1172485112" MODIFIED="1557498707236" TEXT="nach canConvert">
<node CREATED="1540682731631" ID="ID_1059841081" MODIFIED="1557498707236" TEXT="die Typen, in die man umwandeln kann">
@ -61491,6 +61505,39 @@
</node>
</node>
</node>
<node CREATED="1788380932335" ID="ID_550975867" MODIFIED="1788381357392" TEXT="TypeIdxID">
<linktarget COLOR="#80969f" DESTINATION="ID_550975867" ENDARROW="Default" ENDINCLINATION="-1482;411;" ID="Arrow_ID_1821706956" SOURCE="ID_659200917" STARTARROW="None" STARTINCLINATION="434;28;"/>
<node CREATED="1788381017736" ID="ID_1220983692" MODIFIED="1788381171239" TEXT="die reine Suche gab es schon f&#xfc;r Type-Sequenzen">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
<p>
constexpr <font color="#000000" face="DejaVu Sans Mono"><b>indexOfType</b></font>&lt;<font color="#870505">T,TS...</font>&gt;()
</p>
<p>
</p>
<p>
bisher wenig verwendet, wenn aber, dann f&#252;r einen Index-basierten Zugriff &#10233; es <b>mu&#223;</b>&#160;eine static-Assertion geben, da&#223; der gesuchte Typ auch wirklich in der Liste ist (es w&#228;re brandgef&#228;hrlich, im sonst-Fall ein Sentinel zur&#252;ckzugeben, z.B. -1)
</p>
</body>
</html></richcontent>
</node>
<node CREATED="1788381173379" ID="ID_611234338" MODIFIED="1788381193909" TEXT="konzipiere es damit explizit als Typ-ID">
<node CREATED="1788381195458" ID="ID_1625105480" MODIFIED="1788381212466" TEXT="soll 0 sein f&#xfc;r &#xbb;alle anderen&#xab;"/>
<node COLOR="#17155b" CREATED="1788381224205" ID="ID_1878301364" MODIFIED="1788381344411" TEXT="verdammt kniffelig ... letztlich aber geknackt">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
<p>
der Trick war, den gefundenen Index in einem zus&#228;tzlichen non-type-Argument hochzuz&#228;hlen, und bei Match von dort zu entnehmen. Warum? nur so kann man <i>einen ganz anderen Wert</i>&#160;liefern, wenn man &#252;ber das Ende der Liste hinausl&#228;uft; die naive Implementierung mit Tail-Rekursion addiert ja den Index <i>auf dem R&#252;ckweg hoch</i>&#160;und erlaubt daher keinen alternativen Ausgang
</p>
</body>
</html></richcontent>
</node>
</node>
</node>
</node>
<node COLOR="#338800" CREATED="1775068804117" FOLDED="true" ID="ID_528287612" MODIFIED="1775585854666" TEXT="Laufzeit-idx Access">
<linktarget COLOR="#2d4868" DESTINATION="ID_528287612" ENDARROW="Default" ENDINCLINATION="-1099;144;" ID="Arrow_ID_1760258574" SOURCE="ID_1844807854" STARTARROW="None" STARTINCLINATION="-935;121;"/>
<icon BUILTIN="button_ok"/>
@ -64126,7 +64173,8 @@
<linktarget COLOR="#313bd5" DESTINATION="ID_297232550" ENDARROW="Default" ENDINCLINATION="147;-4;" ID="Arrow_ID_604220325" SOURCE="ID_1658923821" STARTARROW="None" STARTINCLINATION="117;8;"/>
<icon BUILTIN="flag-yellow"/>
</node>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1775751872730" ID="ID_106564309" MODIFIED="1775770628001" TEXT="damit den bestehenden PolymorphicValue modernisieren">
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1775751872730" ID="ID_106564309" MODIFIED="1788302308822" TEXT="damit den bestehenden PolymorphicValue modernisieren">
<linktarget COLOR="#fef1ad" DESTINATION="ID_106564309" ENDARROW="Default" ENDINCLINATION="377;18;" ID="Arrow_ID_1956727109" SOURCE="ID_1296566156" STARTARROW="None" STARTINCLINATION="297;11;"/>
<icon BUILTIN="flag-yellow"/>
</node>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1775751886640" ID="ID_635074732" MODIFIED="1775770630422" TEXT="und auf dieser Basis die FunInline redefinieren">
@ -64805,7 +64853,8 @@
<node CREATED="1775752824541" ID="ID_1199118483" MODIFIED="1775752834819" TEXT="der Code ist ziemlich schwer zu verstehen"/>
</node>
</node>
<node BACKGROUND_COLOR="#d2beaf" COLOR="#5c4d6e" CREATED="1775752853151" ID="ID_87627416" MODIFIED="1775752859037" TEXT="Re-Implementierung">
<node BACKGROUND_COLOR="#d2beaf" COLOR="#5c4d6e" CREATED="1775752853151" ID="ID_87627416" MODIFIED="1788301725468" TEXT="Re-Implementierung">
<linktarget COLOR="#931557" DESTINATION="ID_87627416" ENDARROW="Default" ENDINCLINATION="-273;3165;" ID="Arrow_ID_867915966" SOURCE="ID_1451113864" STARTARROW="None" STARTINCLINATION="289;-1009;"/>
<icon BUILTIN="hourglass"/>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1775752860084" ID="ID_1520505813" MODIFIED="1775769457487" TEXT="Idee: ein Instance-Manager-Interface schaffen">
<linktarget COLOR="#feefb5" DESTINATION="ID_1520505813" ENDARROW="Default" ENDINCLINATION="22;-857;" ID="Arrow_ID_960733347" SOURCE="ID_297232550" STARTARROW="None" STARTINCLINATION="-127;7;"/>
@ -64821,6 +64870,17 @@
</html></richcontent>
<node CREATED="1775752933506" ID="ID_868304108" MODIFIED="1775752972169" TEXT="w&#xe4;re direkt implementierbar als Komponente, ohne Virtualisierung"/>
<node CREATED="1775752903046" ID="ID_1216439634" MODIFIED="1775752913919" TEXT="man k&#xf6;nnte den VirtualCopySupport direkt darauf aufsetzen"/>
<node CREATED="1788302260005" ID="ID_1296566156" MODIFIED="1788302573075" TEXT="auch bei der Idee &#xbb;FunInline&#xab; hatte ich PolymorphicValue in Erw&#xe4;gung gezogen">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
<p>
...war mir aber letztlich nicht schl&#252;ssig, in welche Richtung meine Abw&#228;gung geht; die C++-STDLIB verwendet ja <i>zwei Funktionspointer</i>, von denen einer auf einen generischen Instance-Manager zeigt. Meine eigenen &#187;Freihand-Abw&#228;gungen&#171; bez&#252;glich generierter Assembly und Runtime-Overhead weisen aber immer wieder in die Richtung, da&#223; eine VTable effizienter ist, als mehrere Funktionspointer, wobei im Fall von lediglich zwei Pointern vermutlich immer noch nahezu &#196;quivalenz besteht. Das Problem bei solchen Abw&#228;gungen im Kontext von LIbrary-Design ist, da&#223; man die Frage eigentlich nicht empirisch entscheiden kann; Microbenchmarks sind immer nur Momentaufnahmen, und der globale Impact einer solchen Entscheidung ist extrem schwer zu fassen (und aufwendig zu untersuchen)
</p>
</body>
</html></richcontent>
<arrowlink COLOR="#fef1ad" DESTINATION="ID_106564309" ENDARROW="Default" ENDINCLINATION="377;18;" ID="Arrow_ID_1956727109" STARTARROW="None" STARTINCLINATION="297;11;"/>
</node>
</node>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1775769404408" ID="ID_862372565" LINK="https://issues.lumiera.org/ticket/1421" MODIFIED="1775769417192" TEXT="#1421 define Instance-Manager interface">
<icon BUILTIN="flag-yellow"/>
@ -64828,6 +64888,13 @@
</node>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1775769220570" ID="ID_572028635" LINK="https://issues.lumiera.org/ticket/1197" MODIFIED="1775769238759" TEXT="#1197 rationalise copy support in PolymorphicValue">
<icon BUILTIN="flag-yellow"/>
<node BACKGROUND_COLOR="#e0ceaa" COLOR="#690f14" CREATED="1788302637488" HGAP="32" ID="ID_335130787" LINK="#ID_1782676400" MODIFIED="1788302782855" TEXT="....und der generische Copy-Support sollte auf copy-and-swap aufbauen" VSHIFT="2">
<font NAME="SansSerif" SIZE="11"/>
<icon BUILTIN="idea"/>
</node>
<node CREATED="1788302603281" ID="ID_324413890" MODIFIED="1788302793158" TEXT="ebenso wichtig: Payload mu&#xdf; &#xbb;in-place&#xab; konstruierbar sein">
<icon BUILTIN="messagebox_warning"/>
</node>
</node>
</node>
</node>
@ -82935,7 +83002,7 @@
</html></richcontent>
</node>
</node>
<node CREATED="1783092344401" ID="ID_723247866" MODIFIED="1783092356166" TEXT="ParamType">
<node CREATED="1783092344401" ID="ID_723247866" MODIFIED="1788306366293" TEXT="Provision">
<node CREATED="1783092477119" ID="ID_1734714581" MODIFIED="1783092481906" TEXT="Interfaface">
<node CREATED="1783092482966" ID="ID_1196126403" MODIFIED="1783092486026" TEXT="virtuell"/>
<node CREATED="1783092486716" ID="ID_1507254773" MODIFIED="1783092489572" TEXT="generisch">
@ -82967,8 +83034,17 @@
</node>
</node>
</node>
<node CREATED="1783101507062" ID="ID_1298955481" MODIFIED="1783101521840" TEXT="Header: lib/par/param-type.hpp|cpp">
<node CREATED="1783101523306" ID="ID_1764325281" MODIFIED="1783172855177" TEXT="hier auch die Type-Registry"/>
<node CREATED="1783101507062" ID="ID_1298955481" MODIFIED="1788306389082" TEXT="Header....">
<node CREATED="1788306396605" ID="ID_1497186410" MODIFIED="1788306410252" TEXT="lib/par/provision.hpp">
<node CREATED="1788306414146" HGAP="71" ID="ID_833702080" MODIFIED="1788306467320" TEXT="Buffer-Zugriffs-Mechanik" VSHIFT="2">
<font NAME="SansSerif" SIZE="10"/>
</node>
</node>
<node CREATED="1788306390020" ID="ID_1994320454" MODIFIED="1788306392775" TEXT="lib/par/param-type.hpp|cpp">
<node CREATED="1783101523306" HGAP="29" ID="ID_1764325281" MODIFIED="1788306464746" TEXT="hier auch die Type-Registry" VSHIFT="2">
<font NAME="SansSerif" SIZE="10"/>
</node>
</node>
</node>
</node>
<node CREATED="1783097554556" ID="ID_1339731751" MODIFIED="1783097566222" TEXT="Domain">
@ -82995,7 +83071,7 @@
<node BACKGROUND_COLOR="#c8c0b6" CREATED="1784489444352" ID="ID_1412623970" MODIFIED="1784489521150" TEXT="doch! das funktioniert weiterhin">
<icon BUILTIN="idea"/>
</node>
<node CREATED="1784489483382" ID="ID_617432070" MODIFIED="1787695360380">
<node CREATED="1784489483382" ID="ID_617432070" MODIFIED="1788284693233">
<richcontent TYPE="NODE"><html>
<head/>
<body>
@ -83030,7 +83106,7 @@
</p>
</body>
</html></richcontent>
<linktarget COLOR="#ffe99c" DESTINATION="ID_617432070" ENDARROW="Default" ENDINCLINATION="236;9;" ID="Arrow_ID_1412212027" SOURCE="ID_711986937" STARTARROW="None" STARTINCLINATION="236;9;"/>
<linktarget COLOR="#ffe99c" DESTINATION="ID_617432070" ENDARROW="Default" ENDINCLINATION="184;7;" ID="Arrow_ID_1412212027" SOURCE="ID_711986937" STARTARROW="None" STARTINCLINATION="162;6;"/>
<linktarget COLOR="#fe8953" DESTINATION="ID_617432070" ENDARROW="Default" ENDINCLINATION="368;0;" ID="Arrow_ID_1535827259" SOURCE="ID_1219008003" STARTARROW="None" STARTINCLINATION="463;38;"/>
</node>
</node>
@ -83090,11 +83166,11 @@
<node COLOR="#352c84" CREATED="1784491298401" ID="ID_427305032" MODIFIED="1784491298401" TEXT="Fazit {generiertes Multi-TypeHandler-OO-Interface}">
<font BOLD="true" NAME="SansSerif" SIZE="12"/>
<icon BUILTIN="forward"/>
<node CREATED="1784491360016" ID="ID_711986937" MODIFIED="1784491537887" TEXT="das Original-Baumuster von Alexandrescu ist immer noch die beste L&#xf6;sung">
<arrowlink COLOR="#ffe99c" DESTINATION="ID_617432070" ENDARROW="Default" ENDINCLINATION="236;9;" ID="Arrow_ID_1412212027" STARTARROW="None" STARTINCLINATION="236;9;"/>
<node CREATED="1784491360016" ID="ID_711986937" MODIFIED="1788284693233" TEXT="das Original-Baumuster von Alexandrescu ist immer noch eine elegante L&#xf6;sung">
<arrowlink COLOR="#ffe99c" DESTINATION="ID_617432070" ENDARROW="Default" ENDINCLINATION="184;7;" ID="Arrow_ID_1412212027" STARTARROW="None" STARTINCLINATION="162;6;"/>
</node>
<node CREATED="1784491373675" ID="ID_1952132123" MODIFIED="1784491392120" TEXT="die Implementierung per Chain braucht keine Sichtbarkeit der anderen Overloads"/>
<node BACKGROUND_COLOR="#e0ceaa" COLOR="#690f14" CREATED="1784491392987" ID="ID_1626670078" MODIFIED="1784491428279" TEXT="auf Ambiguit&#xe4;ten in den Typ-Signaturen achten">
<node BACKGROUND_COLOR="#e0ceaa" COLOR="#690f14" CREATED="1784491392987" ID="ID_1626670078" MODIFIED="1788284654454" TEXT="auf Ambiguit&#xe4;ten in den Typ-Signaturen achten">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
@ -83103,6 +83179,7 @@
</p>
</body>
</html></richcontent>
<linktarget COLOR="#474ebe" DESTINATION="ID_1626670078" ENDARROW="Default" ENDINCLINATION="317;19;" ID="Arrow_ID_1833189754" SOURCE="ID_35862304" STARTARROW="None" STARTINCLINATION="396;16;"/>
<icon BUILTIN="clanbomber"/>
</node>
</node>
@ -83117,7 +83194,7 @@
</body>
</html></richcontent>
</node>
<node BACKGROUND_COLOR="#fafe99" COLOR="#fa002a" CREATED="1788209315295" ID="ID_279904556" MODIFIED="1788210268056" TEXT="VTables bl&#xe4;hen sich auf">
<node COLOR="#435e98" CREATED="1788209315295" ID="ID_279904556" MODIFIED="1788284583155" TEXT="VTables bl&#xe4;hen sich auf">
<icon BUILTIN="broken-line"/>
<node CREATED="1788209326125" ID="ID_1531181426" MODIFIED="1788209343878" TEXT="Mix-in &#x27f9; schlie&#xdf;t jedes Sub-Objekt komplett mit ein">
<node CREATED="1788210282924" ID="ID_1520344652" MODIFIED="1788210493326" TEXT="zwar gibt C++ keinerlei Garantien zum Daten-Layout (au&#xdf;er f&#xfc;r PODs)">
@ -83164,10 +83241,23 @@
</html></richcontent>
</node>
</node>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1788211053578" ID="ID_1121107125" MODIFIED="1788214912904" TEXT="Also &#x27f9; mu&#xdf; doch umstellen auf eine lineare Kette &#x2014; auch f&#xfc;r die Interfaces">
<linktarget COLOR="#f91755" DESTINATION="ID_1121107125" ENDARROW="Default" ENDINCLINATION="-1456;53;" ID="Arrow_ID_1757832686" SOURCE="ID_1738529643" STARTARROW="None" STARTINCLINATION="-304;11;"/>
<node COLOR="#435e98" CREATED="1788211053578" ID="ID_1121107125" MODIFIED="1788284625243" TEXT="Also &#x27f9; mu&#xdf; doch umstellen auf eine lineare Kette &#x2014; auch f&#xfc;r die Interfaces">
<linktarget COLOR="#a81651" DESTINATION="ID_1121107125" ENDARROW="Default" ENDINCLINATION="-1456;53;" ID="Arrow_ID_1757832686" SOURCE="ID_1738529643" STARTARROW="None" STARTINCLINATION="-297;13;"/>
<icon BUILTIN="yes"/>
</node>
<node COLOR="#0c5669" CREATED="1788284754476" ID="ID_653345776" MODIFIED="1788284851663" TEXT="nun Assert im Test auf Gr&#xf6;&#xdf;e des Basis-Interfaces">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
<p>
...was nicht komplett durch den C++ - Standard gedeckt ist, jedoch aufgrund der Alignment-Contstraints und der Pflicht zur zero-overhead-Implementierung praktisch immer gegeben sein d&#252;rfte
</p>
</body>
</html></richcontent>
</node>
<node BACKGROUND_COLOR="#c8c0b6" COLOR="#435e98" CREATED="1788284591681" ID="ID_35862304" MODIFIED="1788284660301" TEXT="Fazit: etwas kniffligere Definition &#x2014; aber weniger Ambituit&#xe4;ts-Probleme">
<arrowlink COLOR="#474ebe" DESTINATION="ID_1626670078" ENDARROW="Default" ENDINCLINATION="317;19;" ID="Arrow_ID_1833189754" STARTARROW="None" STARTINCLINATION="396;16;"/>
</node>
</node>
</node>
</node>
@ -83950,7 +84040,7 @@
<node CREATED="1788013034593" ID="ID_1225110265" MODIFIED="1788013038934" TEXT="eine Provision"/>
<node CREATED="1788014082405" ID="ID_100431217" MODIFIED="1788014088031" TEXT="das ParamType-Interace"/>
<node CREATED="1788014092867" ID="ID_1527036015" MODIFIED="1788017590529" TEXT="polyvalue::CopySupport - Marker">
<node CREATED="1788017597647" ID="ID_1451113864" LINK="https://issues.lumiera.org/ticket/1197" MODIFIED="1788020032021" TEXT="stelle fest: PolymorphicValue ist schon recht verwirrend implementiert">
<node BACKGROUND_COLOR="#e0ceaa" COLOR="#690f14" CREATED="1788017597647" ID="ID_1451113864" LINK="https://issues.lumiera.org/ticket/1197" MODIFIED="1788301852253" TEXT="stelle fest: PolymorphicValue ist schon recht verwirrend implementiert">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
@ -83979,6 +84069,17 @@
</ul>
</body>
</html></richcontent>
<arrowlink COLOR="#931557" DESTINATION="ID_87627416" ENDARROW="Default" ENDINCLINATION="-273;3165;" ID="Arrow_ID_867915966" STARTARROW="None" STARTINCLINATION="289;-1009;"/>
<icon BUILTIN="clanbomber"/>
<node BACKGROUND_COLOR="#e0ceaa" COLOR="#af020b" CREATED="1788301729827" ID="ID_18695637" MODIFIED="1788386325808" TEXT="erscheint zunehmend dringend...">
<linktarget COLOR="#ff2137" DESTINATION="ID_18695637" ENDARROW="Default" ENDINCLINATION="1165;103;" ID="Arrow_ID_1244208579" SOURCE="ID_1978220833" STARTARROW="None" STARTINCLINATION="349;18;"/>
<linktarget COLOR="#ff2137" DESTINATION="ID_18695637" ENDARROW="Default" ENDINCLINATION="1165;103;" ID="Arrow_ID_635472113" SOURCE="ID_1100385220" STARTARROW="None" STARTINCLINATION="373;14;"/>
<font NAME="SansSerif" SIZE="11"/>
</node>
<node BACKGROUND_COLOR="#d2beaf" COLOR="#5c4d6e" CREATED="1788301751355" ID="ID_1968045723" MODIFIED="1788301772221" TEXT="in diesem (oder dem n&#xe4;chsten) VerticalSlice angehen">
<font NAME="SansSerif" SIZE="11"/>
<icon BUILTIN="yes"/>
</node>
</node>
<node CREATED="1788017707090" ID="ID_308578833" MODIFIED="1788018098862" TEXT="man mu&#xdf; nur ein Marker-Interface implementieren (um beim Kopieren zu kooperieren)">
<richcontent TYPE="NOTE"><html>
@ -84080,7 +84181,20 @@
</html></richcontent>
</node>
</node>
<node CREATED="1788020869700" ID="ID_57699637" MODIFIED="1788020888892" TEXT="klar ist: wenn es einen &#xbb;Buffer&#xab; gibt, dann residiert er hier, in der Provision"/>
<node COLOR="#5b280f" CREATED="1788020869700" ID="ID_57699637" MODIFIED="1788380239674" TEXT="klar ist: wenn es einen &#xbb;Buffer&#xab; gibt, dann residiert er hier, in der Provision">
<icon BUILTIN="button_cancel"/>
<node CREATED="1788380241393" ID="ID_258414787" MODIFIED="1788380272992" TEXT="Nein! definitiv nicht &#x27f6; das bricht die Abstraktion (&#xbb;Datenquelle&#xab;)"/>
<node CREATED="1788380280763" ID="ID_1135171473" MODIFIED="1788380317432" TEXT="der &#xbb;Buffer&#xab; geh&#xf6;rt in einen (opaquen) Implementierungs-Typ">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
<p>
ich will mich ja <i>grade nicht darauf festlegen</i>, da&#223; es einen &#187;Buffer&#171; gibt
</p>
</body>
</html></richcontent>
</node>
</node>
<node CREATED="1788021229355" ID="ID_1822130411" MODIFIED="1788021252164" TEXT="Provision&amp; k&#xf6;nnte eine Dekorator-Kette bilden">
<node CREATED="1788022402071" ID="ID_37196039" MODIFIED="1788022413073" TEXT="damit k&#xf6;nnte auch das &#xbb;Setzen&#xab; delegiert werden"/>
<node CREATED="1788022413763" ID="ID_241754503" MODIFIED="1788022585515" TEXT="aber unklar: wie wird der Typ ausgedr&#xfc;ckt?"/>
@ -84166,6 +84280,11 @@
</html></richcontent>
</node>
</node>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1788403986153" ID="ID_1976191283" MODIFIED="1788404065349" TEXT="&#xbb;Typ&#xab; hei&#xdf;t nun &#x27fc; TypedEntity&lt;VAL&gt;">
<icon BUILTIN="yes"/>
<node CREATED="1788404020598" ID="ID_1755481124" MODIFIED="1788404034549" TEXT="das bedeutet: es ist nun ein Implementierungs-Service"/>
<node CREATED="1788404035161" ID="ID_470583685" MODIFIED="1788404044976" TEXT="und wird auf den Parameter-Basis-Typ getemplated"/>
</node>
</node>
<node CREATED="1788125003779" ID="ID_1750350767" MODIFIED="1788125413347" TEXT="(dynamische) Provision">
<node CREATED="1788125418166" ID="ID_1175365111" MODIFIED="1788125431416" TEXT="erfordert weiteren &#xbb;Slot&#xab; f&#xfc;r ein Delegate"/>
@ -84335,7 +84454,7 @@
</p>
</body>
</html></richcontent>
<arrowlink COLOR="#f91755" DESTINATION="ID_1121107125" ENDARROW="Default" ENDINCLINATION="-1456;53;" ID="Arrow_ID_1757832686" STARTARROW="None" STARTINCLINATION="-304;11;"/>
<arrowlink COLOR="#a81651" DESTINATION="ID_1121107125" ENDARROW="Default" ENDINCLINATION="-1456;53;" ID="Arrow_ID_1757832686" STARTARROW="None" STARTINCLINATION="-297;13;"/>
</node>
<node BACKGROUND_COLOR="#f8f1cb" COLOR="#a50125" CREATED="1788207092440" ID="ID_1489003663" MODIFIED="1788214784231" TEXT="Typ und BaseDomain werden zum Problem">
<icon BUILTIN="messagebox_warning"/>
@ -84354,8 +84473,16 @@
<icon BUILTIN="messagebox_warning"/>
</node>
</node>
<node CREATED="1788207233069" ID="ID_403725711" MODIFIED="1788207254569" TEXT="aber die konkrete Scale mu&#xdf; darauf aufbauen (da sie Werte beschr&#xe4;nkt)"/>
<node CREATED="1788215170120" ID="ID_1317810371" MODIFIED="1788215194280" TEXT="Typ mu&#xdf; konkret sein, schlie&#xdf;t BaseDomain ein und verweist auf Scale"/>
<node CREATED="1788207233069" ID="ID_403725711" MODIFIED="1788207254569" TEXT="aber die konkrete Scale mu&#xdf; darauf aufbauen (da sie Werte beschr&#xe4;nkt)">
<node CREATED="1788277709450" HGAP="60" ID="ID_1575437557" MODIFIED="1788277762386" TEXT="&#x201e;aufbauen&#x201c; hei&#xdf;t nicht zwangsl&#xe4;ufig auch &#x201e;erweitern&#x201c;" VSHIFT="1">
<icon BUILTIN="idea"/>
</node>
</node>
<node CREATED="1788215170120" ID="ID_1317810371" MODIFIED="1788215194280" TEXT="Typ mu&#xdf; konkret sein, schlie&#xdf;t BaseDomain ein und verweist auf Scale">
<node CREATED="1788279901620" HGAP="78" ID="ID_1647252878" MODIFIED="1788279934225" TEXT="umbenennen in &#x27fc; TypedEntity" VSHIFT="1">
<icon BUILTIN="yes"/>
</node>
</node>
</node>
<node BACKGROUND_COLOR="#fdfdcf" COLOR="#ff0000" CREATED="1788215427662" ID="ID_214321685" MODIFIED="1788217785702" TEXT="Das Povision-Interface mu&#xdf; anders angeordnet werden">
<linktarget COLOR="#ff001d" DESTINATION="ID_214321685" ENDARROW="Default" ENDINCLINATION="4;-14;" ID="Arrow_ID_1991058182" SOURCE="ID_1569730697" STARTARROW="None" STARTINCLINATION="-120;4;"/>
@ -84371,7 +84498,16 @@
</html></richcontent>
<node CREATED="1788215575560" ID="ID_690071422" MODIFIED="1788215606429" TEXT="das ist das front-End"/>
<node CREATED="1788215613679" ID="ID_200801579" MODIFIED="1788215624951" TEXT="somit wird hier auch eine Interface-Kette eingemischt"/>
<node CREATED="1788215708763" ID="ID_907924223" MODIFIED="1788215727096" TEXT="oder man w&#xfc;rde Zugang zu einer Provision bieten"/>
<node CREATED="1788215708763" ID="ID_907924223" MODIFIED="1788277831015" TEXT="oder man w&#xfc;rde Zugang zu einer Provision bieten">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
<p>
bedeutet, es gibt eine Methode um eine Provision&amp; zu bekommen, welche konsequenterweise dann &#252;ber das Implementierungs-Interface erreichbar sein mu&#223; (da wir uns auf eine einfache Vererbungskette einschr&#228;nken m&#252;ssen)
</p>
</body>
</html></richcontent>
</node>
</node>
<node CREATED="1788215737795" ID="ID_516807030" MODIFIED="1788215749277" TEXT="Provision wird damit ein eigenst&#xe4;ndiges Interface">
<node CREATED="1788215750841" ID="ID_374789197" MODIFIED="1788215911279" TEXT="sie ist nur implizit getypt">
@ -84402,12 +84538,12 @@
</html></richcontent>
</node>
</node>
<node CREATED="1788221594093" ID="ID_579519208" MODIFIED="1788221708229" TEXT="es mu&#xdf; aber per default als NOP implementiert sein">
<node CREATED="1788221594093" ID="ID_579519208" MODIFIED="1788279294776" TEXT="es mu&#xdf; aber per default als NOP implementiert sein">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
<p>
...sonst wird es schwierig mit dem Zusammenstellen der Interface-Kette; tats&#228;chlich lassen sich alle f&#252;r dieses Interface vorgesehenen Operationen &#187;leer&#171; Implementieren &#8212; es passiert dann einfach gar nichts, keine Zuweisung, keine Verbindung
...sonst wird es schwierig mit dem Zusammenstellen der Interface-Kette; tats&#228;chlich lassen sich alle f&#252;r dieses Interface vorgesehenen Operationen &#187;leer&#171; Implementieren&#160;&#8212; es passiert dann einfach gar nichts, keine Zuweisung, keine Verbindung &#8212; was inhaltlich-logisch sogar korrekt ist, ein NICHTS-Parameter...
</p>
</body>
</html></richcontent>
@ -84420,6 +84556,352 @@
<node CREATED="1788222535392" ID="ID_1282201343" MODIFIED="1788222543419" TEXT="Disposition ist immer noch ein Interface"/>
<node CREATED="1788222544142" ID="ID_1947215779" MODIFIED="1788222568288" TEXT="es wird per PolymorphicValue auf das Parameter-Objekt exponiert"/>
<node CREATED="1788222571539" ID="ID_1256386409" MODIFIED="1788222603029" TEXT="die ganze konkrete Implementierung setzt darauf auf (und bleibt damit opaque, und variierbar)"/>
<node BACKGROUND_COLOR="#c8bed8" COLOR="#3e3976" CREATED="1788293527789" ID="ID_1979935695" MODIFIED="1788296915688" TEXT="Konsequenz &#x27f9; mu&#xdf; dieses Interface generisch zusammenstellen">
<icon BUILTIN="yes"/>
<node CREATED="1788293568866" ID="ID_131380857" MODIFIED="1788380416055" TEXT="es mu&#xdf; noch unterhalb der getypten Implementierung liegen"/>
<node CREATED="1788380418977" ID="ID_626646433" MODIFIED="1788380435831" TEXT="es mu&#xdf; bereits einen ID-Record bieten">
<node CREATED="1788380437998" ID="ID_1881580962" MODIFIED="1788380488048" TEXT="sonst ist kein &#xbb;short-circuit&#xab; m&#xf6;glich">
<arrowlink COLOR="#7a6a8b" DESTINATION="ID_1468282295" ENDARROW="Default" ENDINCLINATION="116;-139;" ID="Arrow_ID_582693889" STARTARROW="None" STARTINCLINATION="220;17;"/>
</node>
</node>
<node CREATED="1788293586698" ID="ID_1746668987" MODIFIED="1788293628728" TEXT="Inhaltlich geh&#xf6;rt es aber n&#xe4;her zum ParamData-Record"/>
</node>
</node>
<node CREATED="1788279465992" ID="ID_511934631" MODIFIED="1788307762955" TEXT="Insgesamt entsteht hier eine Konkretisierungs-Kette">
<linktarget COLOR="#4d65b9" DESTINATION="ID_511934631" ENDARROW="Default" ENDINCLINATION="-379;20;" ID="Arrow_ID_927557846" SOURCE="ID_1002785268" STARTARROW="None" STARTINCLINATION="119;14;"/>
<icon BUILTIN="forward"/>
<node CREATED="1788279482831" ID="ID_1252818882" MODIFIED="1788279536466" TEXT="wir gehen vom Kontrakt zum Service">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
<p>
es handelt sich dabei durchgehend um Abstraktionen, wobei sich jedoch der Charakter der Abstraktion &#228;ndert von einer Zusicherung zu etwas, auf dem wir konkret aufbauen k&#246;nnen
</p>
</body>
</html></richcontent>
</node>
<node CREATED="1788279539424" ID="ID_1639736337" MODIFIED="1788279543780" TEXT="Bedeutung der Stufen">
<node CREATED="1788279549319" ID="ID_120197629" MODIFIED="1788279575207" TEXT="Provision: die Grundidee eines Parameters wie hier konzeptionalisiert"/>
<node CREATED="1788279579772" ID="ID_1387667429" MODIFIED="1788279619787" TEXT="Domain: Zusicherung einer Typ-konformen Handhabung"/>
<node CREATED="1788280039452" ID="ID_1355845527" MODIFIED="1788295973732" TEXT="Disposition: der vollst&#xe4;ndige Parameter-Implementierungs-Service"/>
<node CREATED="1788279649921" ID="ID_829245549" MODIFIED="1788279664995" TEXT="BaseDomain: Festlegung der Eigenschaften der Datenbasis"/>
<node CREATED="1788279667230" ID="ID_1645392786" MODIFIED="1788279840724" TEXT="TypedEntity: Konformit&#xe4;t und Darstelluns-F&#xe4;higkeiten"/>
<node CREATED="1788295927324" ID="ID_53887849" MODIFIED="1788295946230" TEXT="ParamData: der komplette Implementierungs-Record"/>
</node>
<node COLOR="#338800" CREATED="1788296967307" ID="ID_1067952271" MODIFIED="1788296982864" TEXT="damit ist f&#xfc;r jeden Belang eine Ebene festgelegt">
<icon BUILTIN="idea"/>
</node>
<node BACKGROUND_COLOR="#eef0c5" COLOR="#990000" CREATED="1788296987347" ID="ID_1409086602" MODIFIED="1788297005246" TEXT="kann nun die Implementierung konstruieren">
<icon BUILTIN="pencil"/>
<node COLOR="#435e98" CREATED="1788307857528" ID="ID_412964688" MODIFIED="1788313299843" TEXT="Value-Init &#x27f6; direkt vom Builder in den Konstruktor"/>
<node CREATED="1788307874399" ID="ID_195138202" MODIFIED="1788307912949" TEXT="Get mit Typ-Konversion &#x27f6; generisches front-End auf dem Disposition-Interface">
<node CREATED="1788307916543" ID="ID_877977052" MODIFIED="1788307932499" TEXT="so mu&#xdf; es sein &#x2014; daf&#xfc;r haben wir ein Interface"/>
<node CREATED="1788307933286" ID="ID_67518693" MODIFIED="1788307948939" TEXT="die Implementierung baut dann auf den Basis-Interfaces auf">
<node CREATED="1788366990200" ID="ID_1939303972" MODIFIED="1788367012596" TEXT="sch&#xf6;n w&#xe4;rs...">
<icon BUILTIN="smiley-angry"/>
</node>
<node CREATED="1788366994118" ID="ID_143088929" MODIFIED="1788367004585" TEXT="dann l&#xe4;uft aber alles per Indirektion">
<icon BUILTIN="smily_bad"/>
</node>
</node>
<node BACKGROUND_COLOR="#f8f1cb" COLOR="#a50125" CREATED="1788308332698" ID="ID_1468282295" MODIFIED="1788380480854" TEXT="Problem: brauche hier die BaseDomain-ID ohne Indirektion">
<linktarget COLOR="#7a6a8b" DESTINATION="ID_1468282295" ENDARROW="Default" ENDINCLINATION="116;-139;" ID="Arrow_ID_582693889" SOURCE="ID_1881580962" STARTARROW="None" STARTINCLINATION="220;17;"/>
<icon BUILTIN="messagebox_warning"/>
<node CREATED="1788362693945" ID="ID_1951653761" MODIFIED="1788362711453" TEXT="sonst &#xbb;relativiert&#xab; sich der Direkt-Zugriff">
<node CREATED="1788366366118" ID="ID_295761416" MODIFIED="1788366874928" TEXT="tats&#xe4;chlich brauche ich h&#xf6;chstens eine Indirektion">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
<p>
...denn hier habe ich ja (per Template-Parameter) schon einen Typ in der Hand, mu&#223; also nur noch den zugeh&#246;rigen TypeHandler aufrufen (eine Indirektion)
</p>
</body>
</html></richcontent>
</node>
<node CREATED="1788366386901" ID="ID_303065066" MODIFIED="1788366439089" TEXT="der double-Dispatch w&#xe4;re gar nicht notwendig hier">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
<p>
...der deckt nur den (theoretischen) Fall ab, da&#223; wir eine Zuweisung zwischen <i>zwei Parametern</i>&#160;machen (f&#252;r die beide der Datentyp opaque ist).
</p>
</body>
</html></richcontent>
</node>
<node CREATED="1788366876053" ID="ID_871895427" MODIFIED="1788366988849" TEXT="und eine Indirektion um dann per force-Cast zuzugreifen w&#xe4;re Unsinn">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
<p>
zumal ich dann auch noch per force-downcast auf den Buffer zugreifen m&#252;&#223;te
</p>
</body>
</html></richcontent>
<icon BUILTIN="smiley-oh"/>
</node>
</node>
<node BACKGROUND_COLOR="#fed199" COLOR="#b90040" CREATED="1788309764989" ID="ID_137382885" MODIFIED="1788380092658" TEXT="Alarm: das Design geht hier nicht auf">
<arrowlink COLOR="#fe2680" DESTINATION="ID_1551239755" ENDARROW="Default" ENDINCLINATION="191;-241;" ID="Arrow_ID_1230826257" STARTARROW="None" STARTINCLINATION="-740;0;"/>
<linktarget COLOR="#b25193" DESTINATION="ID_137382885" ENDARROW="Default" ENDINCLINATION="-395;29;" ID="Arrow_ID_1892316604" SOURCE="ID_1271224230" STARTARROW="None" STARTINCLINATION="2071;0;"/>
<icon BUILTIN="broken-line"/>
<node CREATED="1788309801877" ID="ID_1982340657" MODIFIED="1788309820758" TEXT="auf der Interface-Ebene fehlen mir relevante Informationen"/>
<node CREATED="1788309821442" ID="ID_1283728464" MODIFIED="1788309832720" TEXT="aber per Voraussetzung will ich keine Indirektion"/>
<node CREATED="1788309836170" ID="ID_1386925847" MODIFIED="1788309890528" TEXT="und das Implementation-Layout sollte komplett frei konfigurierbar bleiben">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
<p>
auch im Hinblick darauf, da&#223; ich sp&#228;ter mal (m&#246;glichst mit dem gleichen generischen Code) auch komplexe Parameter-Typen handhaben m&#246;chte, wie Vektoren, Farb-Tripel und ganze Masken-Parameters&#228;tze...
</p>
</body>
</html></richcontent>
<icon BUILTIN="messagebox_warning"/>
</node>
</node>
<node BACKGROUND_COLOR="#eef0c5" COLOR="#990000" CREATED="1788380554839" ID="ID_1101549379" MODIFIED="1788380577746" TEXT="Kompromi&#xdf;: ziehe einen ID-Record bereits in die Disposition">
<icon BUILTIN="pencil"/>
<node BACKGROUND_COLOR="#c2b6c8" COLOR="#5b280f" CREATED="1788382780349" FOLDED="true" ID="ID_552546860" MODIFIED="1788397901695" TEXT="PolymorphicValue nicht optimal definiert">
<icon BUILTIN="broken-line"/>
<icon BUILTIN="button_cancel"/>
<node CREATED="1788301325125" ID="ID_1978220833" MODIFIED="1788386325808" TEXT="das mit dem CopySupport ist ein echtes Problem ">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
<p>
Der Umstand, da&#223; man da so ein Marker-Template inmischen mu&#223;, und dann die Fallunterscheidung, wann der PolymorphicValue-Container tats&#228;chlich die schlanke lineare Vererbungskette nutzen kann, und wo der Copy-Adapter aufgesetzt wird....
</p>
<p>
Ich hab das Zeug gebaut, und schon ein paar mal verwendet, aber <i>ich blick' da einfach nicht mehr durch</i>&#160;&#8212; jedes mal mu&#223; man sich wieder durch die ganzen Templates durchfressen (und das f&#252;r etwas, was es eigentlich mit modernem C++ gar nicht mehr br&#228;uchte)
</p>
</body>
</html></richcontent>
<arrowlink COLOR="#ff2137" DESTINATION="ID_18695637" ENDARROW="Default" ENDINCLINATION="1165;103;" ID="Arrow_ID_1244208579" STARTARROW="None" STARTINCLINATION="349;18;"/>
<icon BUILTIN="smiley-angry"/>
</node>
<node BACKGROUND_COLOR="#e0ceaa" COLOR="#690f14" CREATED="1788383059641" ID="ID_1688642617" MODIFIED="1788386316028" TEXT="das Marker-Template mu&#xdf; wirklich in der Kette liegen">
<richcontent TYPE="NOTE"><html>
<head>
</head>
<body>
<p>
...ich hatte es zwar definiert und im Container-Typ angegeben &#8212; aber dann im konkreten API-Aufbau doch nicht eingeschleift (weil es da thematisch ja auch nicht hingeh&#246;rt, Grrrr)
</p>
</body>
</html>
</richcontent>
<icon BUILTIN="broken-line"/>
</node>
<node CREATED="1788384797381" ID="ID_1232714334" MODIFIED="1788386029574" TEXT="stimmt garnicht &#x27f6; es w&#xe4;hlt die optimale Variante">
<icon BUILTIN="idea"/>
<node CREATED="1788384925999" ID="ID_906034232" MODIFIED="1788384956844" TEXT="aber es schl&#xe4;gt den &quot;admin overhead&quot; blindlings oben drauf"/>
<node CREATED="1788384957654" ID="ID_799415187" MODIFIED="1788384990688" TEXT="aber wir verwenden einen sizeof &#x27f6; da ist die VTable bereits mit eingerechnet"/>
<node CREATED="1788384992694" ID="ID_1687522773" MODIFIED="1788385063843" TEXT="also ist auch das Konzept &#xbb;admin-overhead&#xab; in sich verworren (und &#xfc;berfl&#xfc;ssig)">
<richcontent TYPE="NOTE"><html>
<head>
</head>
<body>
<p>
insofern dieses ganze clevere seitw&#228;rige Attachment &#252;berfl&#252;ssig ist;&#160; die einzige zwingende Voraussetzung ist, da&#223; wir eine VTable haben
</p>
</body>
</html>
</richcontent>
</node>
</node>
<node BACKGROUND_COLOR="#c8c0b6" COLOR="#435e98" CREATED="1788386034754" ID="ID_1268627911" MODIFIED="1788386341107" TEXT="L&#xf6;sung">
<icon BUILTIN="idea"/>
<node CREATED="1788386039641" ID="ID_477009340" MODIFIED="1788386053499" TEXT="zweites Template-Argument in ParamData">
<node CREATED="1788386057747" ID="ID_904631655" MODIFIED="1788386082344" TEXT="damit kann dann der Parameter (Container) hier das CopySupport-API injizieren"/>
<node CREATED="1788386085851" ID="ID_1295285894" MODIFIED="1788386098957" TEXT="und wir halten die Komplexit&#xe4;t nur an einer stelle"/>
</node>
<node BACKGROUND_COLOR="#e0ceaa" COLOR="#690f14" CREATED="1788386101665" ID="ID_93545182" MODIFIED="1788386217575" TEXT="mu&#xdf; die PAYLOAD_SIZE so definieren, da&#xdf; die VTable-size abgezogen wird">
<richcontent TYPE="NOTE"><html>
<head>
</head>
<body>
<p>
weil PolymorphicValue da blindlings seinen ADMIN_OVERHEAD draufschl&#228;gt. Das ist ein sekund&#228;res Problem im API-Design &#8212; wenn das Marker-API und der &#187;workaround&#171; mit dem Mix-in nicht mehr gebraucht werden, dann f&#228;llt auch diese ganze Verwirrung hier weg (die mich jetzt viele Stunden gekostet hat)
</p>
</body>
</html>
</richcontent>
<icon BUILTIN="messagebox_warning"/>
</node>
</node>
<node COLOR="#338800" CREATED="1788386354314" ID="ID_1688624687" MODIFIED="1788386399854" TEXT="jetzt pa&#xdf;ts: sizeof(Parameter) &#x2261; 4 &#xab;slot&#xbb;">
<font NAME="SansSerif" SIZE="11"/>
</node>
</node>
</node>
</node>
</node>
<node CREATED="1788313220539" ID="ID_1678152846" MODIFIED="1788313251138" TEXT="Set mit Typ-Konversion &#x27f6; spiegelblidlich auf dem Disposition-Inteface"/>
<node COLOR="#435e98" CREATED="1788313267301" ID="ID_697595338" MODIFIED="1788313294222" TEXT="Provision: Zugriff auf den Value-Buffer &#x27f6; cast und Assignment"/>
<node CREATED="1788404121292" ID="ID_630136540" MODIFIED="1788404194186">
<richcontent TYPE="NODE"><html>
<head>
</head>
<body>
<p>
<font color="#8c505c" face="DejaVu Sans Mono" size="9pt"><b>ValStorage</b></font>&#160;&#160;: ein konkreter ValBuff mit ausreichender Storage-size
</p>
</body>
</html>
</richcontent>
<icon BUILTIN="forward"/>
<node BACKGROUND_COLOR="#eef0c5" COLOR="#990000" CREATED="1788404196803" ID="ID_569414817" MODIFIED="1788404269415" TEXT="baue statische Type-Spec auf">
<arrowlink COLOR="#578fd2" DESTINATION="ID_1609007571" ENDARROW="Default" ENDINCLINATION="53;-180;" ID="Arrow_ID_486335926" STARTARROW="None" STARTINCLINATION="-29;106;"/>
<icon BUILTIN="pencil"/>
<node CREATED="1788404287935" ID="ID_959512138" MODIFIED="1788404297298" TEXT="Basis-Typ-ID wird generisch erzeugt"/>
<node CREATED="1788404298134" ID="ID_770813391" MODIFIED="1788404312059" TEXT="Storage-Buffer-Size wird automatisch begrenzt"/>
</node>
</node>
</node>
</node>
<node BACKGROUND_COLOR="#fafe99" COLOR="#fa002a" CREATED="1788367103969" ID="ID_1551239755" MODIFIED="1788369873156" TEXT="innere Widerspr&#xfc;che werden deutlich">
<linktarget COLOR="#fe2680" DESTINATION="ID_1551239755" ENDARROW="Default" ENDINCLINATION="191;-241;" ID="Arrow_ID_1230826257" SOURCE="ID_137382885" STARTARROW="None" STARTINCLINATION="-740;0;"/>
<icon BUILTIN="broken-line"/>
<node CREATED="1788367171639" ID="ID_632634612" MODIFIED="1788367181733" TEXT="ich will zugleich zwei Extreme">
<node CREATED="1788367184127" ID="ID_1812755681" MODIFIED="1788367214110" TEXT="ich will einen einfachen Datenwert (&#x27f9;Effizienz)"/>
<node CREATED="1788367215173" ID="ID_1024391215" MODIFIED="1788367223797" TEXT="aber getypt soll der auch sein...."/>
<node CREATED="1788367226489" ID="ID_334299039" MODIFIED="1788367596873" TEXT="und au&#xdf;erdem m&#xf6;chte ich mich JETZT nicht festlegen">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
<p>
...zumal ich einen weiteren gewaltigen Zielkonflikt schon &#187;riechen&#171; kann: die Anspr&#252;che komplexer Datentypen sind mit einem <i>leichtgewichtigen Standardfall</i>&#160;schwer vereinbar.
</p>
</body>
</html></richcontent>
</node>
</node>
<node CREATED="1788367600886" ID="ID_661068668" MODIFIED="1788369878699" TEXT="vermutlich steckt da eine tiefere Problemlage dahinter....">
<linktarget COLOR="#b781a4" DESTINATION="ID_661068668" ENDARROW="Default" ENDINCLINATION="128;148;" ID="Arrow_ID_1562138790" SOURCE="ID_134775037" STARTARROW="None" STARTINCLINATION="-493;26;"/>
<node CREATED="1788367626408" ID="ID_729798008" MODIFIED="1788367646292" TEXT="denn eigentlich ist mir das ganze &#xbb;Paramter&#xab;-Thema im Moment zu viel"/>
<node CREATED="1788367647365" ID="ID_1045440705" MODIFIED="1788367666198">
<richcontent TYPE="NODE"><html>
<head/>
<body>
<p>
ich <b>mu&#223;</b>&#160;es aber anfassen
</p>
</body>
</html></richcontent>
<node CREATED="1788367668144" ID="ID_361160202" MODIFIED="1788367953743" TEXT="weil sich hier eine ganze weitere Dimension im Konzept auftut">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
<p>
Ich habe gesagt: alles was sich vorher regeln l&#228;&#223;t, wird in einer Art Compiler <i>optimal konfiguriert</i>. Und alles &#220;brige sucht mich jetzt als &#187;Parameter&#171; (oder gar Konfiguration und Regelwerk) heim.
</p>
</body>
</html></richcontent>
</node>
<node CREATED="1788367686902" ID="ID_1051533158" MODIFIED="1788367849769" TEXT="weil es ganz gef&#xe4;hrlich mit dem Thema Instanz-Managmenet verkn&#xfc;pft ist">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
<p>
....an den Parameter wird deutlich, da&#223; m&#246;glicherweise meine &#187;L&#246;sung&#171; mit den Segmenten (die ohnehin mehr eine Ausrede ist) so ohne Weiteres gar nicht tragf&#228;hig sein k&#246;nnte &#8212; und wenn sich das realisieren sollte, dann stehe ich unter Handlungszwang (hei&#223;t, ich kann die Architektur nicht l&#228;nger so offen halten, wie ich es gerne h&#228;tte, um den weiterreichenden Ideen die notwendige Luft zu verschaffen)
</p>
</body>
</html></richcontent>
</node>
<node CREATED="1788367954838" ID="ID_542541550" MODIFIED="1788368220121" TEXT="weil ich diesen Pflock einschlagen mu&#xdf; (sonst werden die Pragmatiker das verpfuschen)">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
<p>
Das Thema &#187;Automation&#171; ist eines der wichtigsten Themen, die bestehende Applikationen immer wieder vers&#228;umen. F&#252;r mich ist die L&#246;sung so offensichtlich klar, da&#223; ich es immer in die Zukunft verschoben habe. Nun l&#228;uft mir aber die Zeit davon, dieses Projekt hat keine endlose Zukunft (wenn es sie je gehabt h&#228;tte....). Ich brauche also <i>f&#252;r alle wirklich wichtigen Themen</i>&#160;eine <b>Architektur-L&#246;sung</b>&#160; &#8212; also eine gepr&#228;gte Struktur, die man ohne Zerst&#246;rung nicht &#252;bergehen kann.
</p>
</body>
</html></richcontent>
</node>
</node>
</node>
<node BACKGROUND_COLOR="#ccb59b" COLOR="#6e2a38" CREATED="1788368252238" ID="ID_1087603902" MODIFIED="1788368268125" TEXT="rational betrachtet: die Offenheit des Design ist derzeit das Wichtigste">
<font ITALIC="true" NAME="SansSerif" SIZE="14"/>
<icon BUILTIN="yes"/>
</node>
<node CREATED="1788368277962" ID="ID_422312977" MODIFIED="1788368313545" TEXT="&#x27f9; ich k&#xf6;nnte h&#xf6;chstens einen Ansatzpunkt f&#xfc;r die Effizienz aufzeigen">
<node CREATED="1788368321899" ID="ID_1218702512" MODIFIED="1788368357857" TEXT="dazu m&#xfc;&#xdf;te die Flag-Storage bereits in der Disposition direkt zug&#xe4;nglich sein">
<icon BUILTIN="idea"/>
<node CREATED="1788368361587" ID="ID_1908291843" MODIFIED="1788369980901" TEXT="also ohne Indirektion &#x2014; aber nutzbar f&#xfc;r Subklassen"/>
<node CREATED="1788368368524" ID="ID_1488167235" MODIFIED="1788368381846" TEXT="ich m&#xfc;&#xdf;te mich zwingend auf ein Flag-Datenwort festlegen"/>
<node CREATED="1788368414264" ID="ID_318537304" MODIFIED="1788369253534" TEXT="das ist jedoch die einzige denkbare Alternative zur VTable">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
<p>
Hier mache ich ein ganz grunds&#228;tzliches Argument...
</p>
<ul>
<li>
Parameter sollen universell sein &#10233; also m&#252;ssen sie laufzeit-dynamisch flexibel gemacht werden
</li>
<li>
eine Konfiguration zur Laufzeit erfordert stets eine Storage (auch die VTable)
</li>
<li>
wenn ich unter der Schwelle eines Funktionspointer-Dispatches bleiben m&#246;chte, kann ich nur in von Vornherein festgelegte Code-Alternativen verzweigen, per Flag (oder Compile-Time-Branch)
</li>
</ul>
<p>
<i>Theoretisch</i>&#160;lie&#223;en sich beide Indirektionsmechanismen &#252;ber eine Dispatch-Tabelle verbinden; das w&#228;re aber eine <i>durchaus fragw&#252;rdige</i>&#160;Storage-Optimierung (die ganz sicher unter das Verdikt &#187;premature&#171; f&#228;llt, sofern nicht anders aufgezeigt)
</p>
</body>
</html></richcontent>
</node>
</node>
<node CREATED="1788369259126" ID="ID_773542973" MODIFIED="1788369325763" TEXT="Einsch&#xe4;tzung: ein zweiter &#xbb;Slot&#xab; ist praktisch immer vertretbar...">
<node CREATED="1788369328598" ID="ID_757945751" MODIFIED="1788369847883" TEXT="dann habe ich eben vier &#xbb;Slots&#xab; &#x2014; wtf">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
<p>
unter uns&#228;glichen Schmerzen k&#246;nnte ich daraus drei &#187;Slots&#171; machen ... und was bringt mir das? Wenn ich ultimative Effizienz brauche, sollte ich kein universelles Konstrukt wie einen Parameter verwenden. Siehe die Activity-Language im Scheduler, wo ich durch geeignete Speicher-Anordnung die durchaus massiv vorhandene Indirektion auf aktzeptable Cache-Koh&#228;renz gebracht habe.
</p>
</body>
</html></richcontent>
</node>
<node CREATED="1788369351058" ID="ID_134775037" MODIFIED="1788369878698" TEXT="im Moment leide ich wirklich am &#xbb;Phantomschmerz&#xab;">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
<p>
also echt jetzt! warum bei&#223;e ich mich an der Hinsicht derma&#223;en fest? alle anderen Hinsichten, die ich durchdacht (und bereits gel&#246;st) habe, sind viel wichtiger (z.B. die Automation). Irgendwie versuche ich, hier einen Sieg vor mir selber zu erringen, wobei es doch im Moment gar nichts zu gewinnen gibt.
</p>
</body>
</html></richcontent>
<arrowlink COLOR="#b781a4" DESTINATION="ID_661068668" ENDARROW="Default" ENDINCLINATION="128;148;" ID="Arrow_ID_1562138790" STARTARROW="None" STARTINCLINATION="-493;26;"/>
</node>
</node>
<node BACKGROUND_COLOR="#eef0c5" COLOR="#990000" CREATED="1788380520115" ID="ID_1609007571" MODIFIED="1788404265183" TEXT="f&#xfc;hre also eine generische Spec mit einem ID-Record ein">
<linktarget COLOR="#578fd2" DESTINATION="ID_1609007571" ENDARROW="Default" ENDINCLINATION="53;-180;" ID="Arrow_ID_486335926" SOURCE="ID_569414817" STARTARROW="None" STARTINCLINATION="-29;106;"/>
<icon BUILTIN="pencil"/>
<node CREATED="1788380609599" ID="ID_768311001" MODIFIED="1788380631272" TEXT="und die zugeh&#xf6;rige Storage kommt in die Disposition"/>
<node CREATED="1788380657233" ID="ID_659200917" MODIFIED="1788381357392" TEXT="Neben-Thema: brauche nun eine Basis-Typ-ID">
<arrowlink COLOR="#80969f" DESTINATION="ID_550975867" ENDARROW="Default" ENDINCLINATION="-1482;411;" ID="Arrow_ID_1821706956" STARTARROW="None" STARTINCLINATION="434;28;"/>
<node CREATED="1788381363706" HGAP="31" ID="ID_1985934952" MODIFIED="1788381457346" TEXT="die kann unmittelbar statisch und eindeutig zugewiesen werden" VSHIFT="6">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
<p>
zun&#228;chst dachte ich noch, ich m&#252;&#223;te eine statische Registrierungs-Tabelle aufbauen, ggfs. mit einem Class-Lock. Da ich mich nun aber darauf festgelegt habe, die Basis-Typen statisch festzulegen, in einer Typsequenz, wandert das alles in die Metaprogramming-Ecke
</p>
</body>
</html></richcontent>
</node>
</node>
<node COLOR="#338800" CREATED="1788403805224" ID="ID_35022947" MODIFIED="1788403822452" TEXT="generisches Schema um die Bits im ID-Record zu belegen">
<icon BUILTIN="button_ok"/>
</node>
</node>
</node>
</node>
</node>
<node CREATED="1788134884746" ID="ID_195532610" MODIFIED="1788134888546" TEXT="Builder-Notation">
@ -84440,6 +84922,55 @@
</node>
<node CREATED="1788196981983" ID="ID_832309415" MODIFIED="1788197050345" TEXT="erst dort kann &#xfc;ber den konkreten Typ-Aufbau entschieden werden">
<linktarget COLOR="#4a3c9d" DESTINATION="ID_832309415" ENDARROW="Default" ENDINCLINATION="-1088;45;" ID="Arrow_ID_331072636" SOURCE="ID_97985230" STARTARROW="None" STARTINCLINATION="-455;17;"/>
<node CREATED="1788299705092" ID="ID_1154522601" MODIFIED="1788299716551" TEXT="den Basis-Typ m&#xfc;ssen wir sofort in einen Template-Parameter nehmen"/>
<node CREATED="1788299717240" ID="ID_114328645" MODIFIED="1788299730333" TEXT="aber der Rest (vor allem die Scale) mu&#xdf; noch offen bleiben"/>
</node>
<node CREATED="1788300649206" ID="ID_932127060" MODIFIED="1788304361422" TEXT="sollte Resultat m&#xf6;glichst in-place konstruieren">
<icon BUILTIN="yes"/>
<node CREATED="1788301071029" ID="ID_1356800089" MODIFIED="1788301322838" TEXT="dem steht die bestehende Implementierung von PolymorphicValue im Wege">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
<p>
....diese erscheint heutzutage in mehrfacher Hinsicht als <i>unbeholfen</i>&#160; &#8212; wobei allerdings die Wurzeln noch in die Zeit vor C++11 zur&#252;ckreichen. Im Besonderen gibt es keinen direkt nutzbaren Konstruktor, und auch keine effizienten move-Assignments (copy-and-swap-Idiom). Demzufolge w&#252;rde bereits eine direkte per-Value-Initialisierung der Basisklasse sofort einen Aufruf des virtuellen-Copy-APIs nach sich ziehen....
</p>
</body>
</html></richcontent>
</node>
<node CREATED="1788301325125" ID="ID_1100385220" MODIFIED="1788301843036" TEXT="PolymorphicValue mu&#xdf; definitiv demn&#xe4;chst umfasend modernisiert werden">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
<p>
...da ich dieses Konstrukt zunehmend f&#252;r bedeutsam halte, und in viel gr&#246;&#223;erem Umfang zu verwenden gedenke &#8212; es k&#246;nnte sogar das bisherige ref-count-basiderte Memory-Management im high-level-Model abl&#246;sen....
</p>
</body>
</html></richcontent>
<arrowlink COLOR="#ff2137" DESTINATION="ID_18695637" ENDARROW="Default" ENDINCLINATION="1165;103;" ID="Arrow_ID_635472113" STARTARROW="None" STARTINCLINATION="373;14;"/>
</node>
<node CREATED="1788303471915" ID="ID_1786592729" MODIFIED="1788303488329" TEXT="mu&#xdf; dann wohl direkt den protected-Base-ctor verwenden">
<node CREATED="1788303498632" ID="ID_1722801672" MODIFIED="1788303511627" TEXT="das ist definitiv m&#xf6;glich (und vorgesehen)...."/>
<node CREATED="1788303512343" ID="ID_1972587310" MODIFIED="1788303683341" TEXT="verwendet trickreiches Argument-Matching">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
<p>
....der proctcted-ctor bekommt ein marker-Tag, das definiert ist als IMP* &#8212; dadurch wird der Typ IMP kommuniziert und in einen TypeSelector&lt;IMP&gt; verwandelt ... der dann allerdings erneut indirekt an den eigentlichen Arbeits-ctor weitergetgeben wird. Oh (Herr)mann!
</p>
</body>
</html></richcontent>
</node>
</node>
<node CREATED="1788304299541" ID="ID_1086678671" MODIFIED="1788304357788" TEXT="Builder::build() verl&#xe4;&#xdf;t sich dann auf die RVO">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
<p>
damit <i>sollte laut Standard</i>&#160;der initiale Parameter-Value tats&#228;chlich in-place konstruiert werden, ohne Aufruf des virtuellen copy-support
</p>
</body>
</html></richcontent>
</node>
</node>
</node>
</node>
@ -84448,30 +84979,41 @@
</node>
<node CREATED="1788203329439" ID="ID_1991597342" MODIFIED="1788203340179" TEXT="Parameter-Basisfunktionen">
<node CREATED="1788203369397" ID="ID_1275080112" MODIFIED="1788203381813" TEXT="treibe den Struktur-Aufbau">
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1788203394319" ID="ID_1002785268" MODIFIED="1788203455329" TEXT="Disposition festlegen">
<node COLOR="#435e98" CREATED="1788203394319" ID="ID_1002785268" MODIFIED="1788307769571" TEXT="Disposition festlegen">
<arrowlink COLOR="#4d65b9" DESTINATION="ID_511934631" ENDARROW="Default" ENDINCLINATION="-379;20;" ID="Arrow_ID_927557846" STARTARROW="None" STARTINCLINATION="119;14;"/>
<icon BUILTIN="full-1"/>
</node>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1788203400185" ID="ID_900611719" MODIFIED="1788203458783" TEXT="Builder-Notation schaffen">
<node BACKGROUND_COLOR="#eef0c5" COLOR="#990000" CREATED="1788203400185" ID="ID_900611719" MODIFIED="1788307794257" TEXT="Builder-Notation schaffen">
<icon BUILTIN="full-2"/>
</node>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1788203422590" ID="ID_1249325546" MODIFIED="1788203462519" TEXT="Valure-Konversionen einbinden">
<icon BUILTIN="full-3"/>
<node COLOR="#338800" CREATED="1788313016806" ID="ID_1966722816" MODIFIED="1788403892705" TEXT="generisch per Indirektion">
<icon BUILTIN="button_ok"/>
</node>
<node BACKGROUND_COLOR="#fdfdcf" COLOR="#ff0000" CREATED="1788313027713" ID="ID_1271224230" MODIFIED="1788313367997" TEXT="short-circuit bei direkt passendem Typ">
<arrowlink COLOR="#b25193" DESTINATION="ID_137382885" ENDARROW="Default" ENDINCLINATION="-395;29;" ID="Arrow_ID_1892316604" STARTARROW="None" STARTINCLINATION="2071;0;"/>
<icon BUILTIN="flag-pink"/>
</node>
</node>
</node>
<node BACKGROUND_COLOR="#eef0c5" COLOR="#990000" CREATED="1788203353588" ID="ID_810940322" MODIFIED="1788203359142" TEXT="entwicklen per Parameter_test">
<icon BUILTIN="pencil"/>
<node BACKGROUND_COLOR="#eef0c5" COLOR="#990000" CREATED="1788203485528" ID="ID_1524876130" MODIFIED="1788203551838" TEXT="simpleUsage">
<icon BUILTIN="pencil"/>
<node BACKGROUND_COLOR="#fdfdcf" COLOR="#ff0000" CREATED="1788203491453" ID="ID_1148834637" MODIFIED="1788203559585" TEXT="einfachen unlimitierten int-Parameter erzeugen">
<icon BUILTIN="flag-pink"/>
<node COLOR="#338800" CREATED="1788203485528" ID="ID_1524876130" MODIFIED="1788313089197" TEXT="simpleUsage">
<icon BUILTIN="button_ok"/>
<node COLOR="#338800" CREATED="1788203491453" ID="ID_1148834637" MODIFIED="1788313002273" TEXT="einfachen unlimitierten int-Parameter erzeugen">
<icon BUILTIN="button_ok"/>
</node>
<node BACKGROUND_COLOR="#fdfdcf" COLOR="#ff0000" CREATED="1788203508251" ID="ID_1482426242" MODIFIED="1788203559586" TEXT="diesem einen (typisierten) Wert zuweisen">
<icon BUILTIN="flag-pink"/>
<node COLOR="#338800" CREATED="1788203508251" ID="ID_1482426242" MODIFIED="1788313007743" TEXT="diesem einen (typisierten) Wert zuweisen">
<icon BUILTIN="button_ok"/>
</node>
<node BACKGROUND_COLOR="#fdfdcf" COLOR="#ff0000" CREATED="1788203517810" ID="ID_473781313" MODIFIED="1788203559587" TEXT="den Wert in verschiedene Typen extrahieren">
<icon BUILTIN="flag-pink"/>
<node COLOR="#338800" CREATED="1788203517810" ID="ID_473781313" MODIFIED="1788313011048" TEXT="den Wert in verschiedene Typen extrahieren">
<icon BUILTIN="button_ok"/>
</node>
</node>
<node BACKGROUND_COLOR="#174956" COLOR="#8dfd49" CREATED="1788313090668" ID="ID_684424843" MODIFIED="1788313179645" STYLE="bubble" TEXT="erster einfachster Testfall GR&#xdc;N">
<edge COLOR="#61fe5b" STYLE="bezier" WIDTH="thin"/>
</node>
</node>
</node>
</node>
@ -185803,12 +186345,12 @@ std::cout &lt;&lt; tmpl.render({&quot;what&quot;, &quot;World&quot;}) &lt;&lt; s
</node>
</node>
<node CREATED="1686439783608" ID="ID_25677654" MODIFIED="1686439786528" TEXT="Concepts">
<node CREATED="1686438949795" ID="ID_197491932" LINK="https://stackoverflow.com/a/68238680" MODIFIED="1686439911618" TEXT="Concepts f&#xfc;r Templates">
<node CREATED="1686438949795" ID="ID_197491932" LINK="https://stackoverflow.com/a/68238680" MODIFIED="1686438949795" TEXT="Concepts f&#xfc;r Templates">
<richcontent TYPE="NOTE"><html>
<head/>
<body>
<p>
...also f&#252;r template templtate parameter;
...also f&#252;r template template parameter;
</p>
<p>
f&#252;r diese mu&#223; man allerdings stets die umst&#228;ndlichere <i>requires</i>-Syntax verwenden