ALib C++ Library
Library Version: 2510 R0
Documentation generated by doxygen
Loading...
Searching...
No Matches
formatter.cpp
1// #################################################################################################
2// ALib C++ Library
3//
4// Copyright 2013-2025 A-Worx GmbH, Germany
5// Published under 'Boost Software License' (a free software license, see LICENSE.txt)
6// #################################################################################################
7#include "alib_precompile.hpp"
8#if !defined(ALIB_C20_MODULES) || ((ALIB_C20_MODULES != 0) && (ALIB_C20_MODULES != 1))
9# error "Symbol ALIB_C20_MODULES has to be given to the compiler as either 0 or 1"
10#endif
11#if ALIB_C20_MODULES
12 module;
13#endif
14// ====================================== Global Fragment ======================================
15#include <cmath>
17// =========================================== Module ==========================================
18#if ALIB_C20_MODULES
19 module ALib.Format;
20 import ALib.Lang;
21 import ALib.Strings;
22 import ALib.Boxing;
23#else
24# include "ALib.Lang.H"
25# include "ALib.Strings.H"
26# include "ALib.Boxing.H"
27# include "ALib.Format.H"
28#endif
29// ====================================== Implementation =======================================
31
32using namespace alib::strings;
33
34/// This is the reference documentation module \alib_format.<br>
35/// Extensive documentation for this namespace is provided with the
36/// \ref alib_mod_format "Programmer's Manual" of that module.
37namespace alib::format {
38
40#if !ALIB_SINGLE_THREADED
41 threads::RecursiveLock Formatter::DefaultLock;
42#endif
43
44
45
46#if !DOXYGEN
47
48template<>
49Formatter& Formatter::formatLoop( AString& target, const BoxesMA& args )
52
53 // initialize formatters
54 Formatter* formatter= this;
55 do
56 formatter->initializeFormat();
57 while( (formatter= formatter->Next.Get()) != nullptr );
58
59 // loop over boxes
60 integer argIdx= 0;
61 while ( argIdx < args.Size() - 1 )
62 {
63 String formatString;
64 const Box& actual= args[size_t(argIdx++)];
65 if( actual.IsType<void>() )
66 continue;
67
68 // Either this is a string, or we convert the box to a string. This fetches anything
69 // that is string like, including string-types that are encapsulated in BoxedAs, etc.
70 if( actual.IsArrayOf<character>() )
71 formatString= actual.Unbox<String>();
72 else
73 formatString= formatStringBuffer.Reset( actual );
74
75 if( formatString.IsEmpty() )
76 continue;
77
78 // try each formatter unless one succeeds
79 integer qtyConsume= 0;
80 formatter= this;
81 while( ( qtyConsume= formatter->format( target, formatString, args, int(argIdx ) ) )
82 == 0
83 && (formatter= formatter->Next.Get()) != nullptr )
84 {}
85
86 // no formatter reacted?
87 if( qtyConsume == 0 )
88 // we just append the string...
89 target.template _<NC>( formatString );
90 else
91 // ...otherwise arguments were consumed
92 argIdx+= size_t( qtyConsume );
93 }
94
95 // the last argument was not consumed?
96 if ( argIdx==args.Size() - 1 && !args.back().template IsType<void>() )
97 target.template _<NC>( args.back() );
98 return *this;
99}
100#endif // !DOXYGEN
101
102
103
105{
106 DefaultNumberFormat .Set( &reference.DefaultNumberFormat );
108
109 // if both sub-formatters are of std type, we do the same for them.
110 if( Next && reference.Next )
111 Next->CloneSettings( *reference.Next );
112}
113
114#if !DOXYGEN
115template<>
117{
118 boxes.clear();
119 boxes.Add( args );
120 formatLoop( target, boxes );
121 return *this;
122}
123
124template<>
126{
127 boxes.clear();
128 boxes.Add( args );
129 formatLoop( target, boxes );
130 return *this;
131}
132#endif // !DOXYGEN
133
134} // namespace [alib::format]
135
136
bool IsArrayOf() const
Definition box.inl:587
bool IsType() const
TValue Unbox() const
Definition box.inl:635
TBoxes & Add()
Definition boxes.inl:61
integer Size() const
Definition boxes.inl:163
NumberFormat DefaultNumberFormat
Definition formatter.inl:96
static ALIB_DLL threads::RecursiveLock DefaultLock
virtual ALIB_DLL void CloneSettings(Formatter &reference)
NumberFormat AlternativeNumberFormat
Formatter & formatLoop(AString &target, const boxing::TBoxes< TAllocator > &args)
static ALIB_DLL SPFormatter Default
SharedPtr< Formatter > Next
Formatter()
Default Constructor.
AString formatStringBuffer
A buffer used for conversion of the next argument if it is not of a string-type.
Definition formatter.inl:77
constexpr bool IsEmpty() const
Definition string.inl:367
#define ALIB_BOXING_VTABLE_DEFINE(TMapped, Identifier)
#define ALIB_DCS
Definition alib.inl:1375
#define ALIB_DBG_PREVENT_RECURSIVE_METHOD_CALLS
Definition alib.inl:1349
strings::TAString< character, lang::HeapAllocator > AString
Type alias in namespace alib.
lang::integer integer
Type alias in namespace alib.
Definition integers.inl:149
format::Formatter Formatter
Type alias in namespace alib.
boxing::Box Box
Type alias in namespace alib.
Definition box.inl:1216
boxing::TBoxes< MonoAllocator > BoxesMA
Type alias in namespace alib.
Definition boxes.inl:245
containers::SharedPtr< format::Formatter > SPFormatter
Definition formatter.inl:42
strings::TString< character > String
Type alias in namespace alib.
Definition string.inl:2381
characters::character character
Type alias in namespace alib.