diff --git a/include/dxfeed_graal_cpp_api/event/candle/CandleAlignment.hpp b/include/dxfeed_graal_cpp_api/event/candle/CandleAlignment.hpp index 9489686e..4168519a 100644 --- a/include/dxfeed_graal_cpp_api/event/candle/CandleAlignment.hpp +++ b/include/dxfeed_graal_cpp_api/event/candle/CandleAlignment.hpp @@ -7,9 +7,6 @@ DXFCXX_DISABLE_MSC_WARNINGS_PUSH(4251) -#include "../../internal/utils/StringUtils.hpp" -#include "../../exceptions/InvalidArgumentException.hpp" -#include "../market/MarketEventSymbols.hpp" #include "CandleSymbolAttribute.hpp" #include @@ -58,13 +55,13 @@ struct DXFCPP_EXPORT CandleAlignment : public CandleSymbolAttribute { static const std::unordered_map, dxfcpp::StringHash, std::equal_to<>> BY_STRING; + static const std::vector> VALUES; private: std::string string_{}; - explicit CandleAlignment(const dxfcpp::StringLikeWrapper &string) noexcept : string_{string} { - } + explicit CandleAlignment(const dxfcpp::StringLikeWrapper &string) noexcept; public: CandleAlignment() noexcept = default; @@ -76,10 +73,7 @@ struct DXFCPP_EXPORT CandleAlignment : public CandleSymbolAttribute { * @param symbol The original candle event symbol. * @return candle event symbol string with this candle alignment set. */ - std::string changeAttributeForSymbol(const dxfcpp::StringLikeWrapper &symbol) const override { - return *this == DEFAULT ? MarketEventSymbols::removeAttributeStringByKey(symbol, ATTRIBUTE_KEY) - : MarketEventSymbols::changeAttributeStringByKey(symbol, ATTRIBUTE_KEY, toString()); - } + std::string changeAttributeForSymbol(const dxfcpp::StringLikeWrapper &symbol) const override; /** * Returns string representation of this candle alignment. @@ -88,13 +82,9 @@ struct DXFCPP_EXPORT CandleAlignment : public CandleSymbolAttribute { * * @return string representation of this candle alignment. */ - std::string toString() const { - return string_; - } + std::string toString() const; - bool operator==(const CandleAlignment &candleAlignment) const noexcept { - return string_ == candleAlignment.string_; - } + bool operator==(const CandleAlignment &candleAlignment) const noexcept; /** * Parses string representation of candle alignment into object. @@ -104,23 +94,7 @@ struct DXFCPP_EXPORT CandleAlignment : public CandleSymbolAttribute { * @return The candle alignment (reference) * @throws InvalidArgumentException if the string representation is invalid. */ - static std::reference_wrapper parse(const dxfcpp::StringLikeWrapper &s) { - auto found = BY_STRING.find(s); - - if (found != BY_STRING.end()) { - return found->second; - } - - for (const auto &alignmentRef : VALUES) { - const auto &alignmentStr = alignmentRef.get().toString(); - - if (iEquals(alignmentStr, s)) { - return alignmentRef; - } - } - - throw InvalidArgumentException("Unknown candle alignment: " + s); - } + static std::reference_wrapper parse(const dxfcpp::StringLikeWrapper &s); /** * Returns candle alignment of the given candle symbol string. @@ -129,12 +103,7 @@ struct DXFCPP_EXPORT CandleAlignment : public CandleSymbolAttribute { * @param symbol The candle symbol string. * @return candle alignment of the given candle symbol string. */ - static std::reference_wrapper - getAttributeForSymbol(const dxfcpp::StringLikeWrapper &symbol) { - auto stringOpt = MarketEventSymbols::getAttributeStringByKey(symbol, ATTRIBUTE_KEY); - - return !stringOpt ? std::cref(DEFAULT) : parse(stringOpt.value()); - } + static std::reference_wrapper getAttributeForSymbol(const dxfcpp::StringLikeWrapper &symbol); /** * Returns candle symbol string with the normalized representation of the candle alignment attribute. @@ -142,32 +111,7 @@ struct DXFCPP_EXPORT CandleAlignment : public CandleSymbolAttribute { * @param symbol The candle symbol string. * @return candle symbol string with the normalized representation of the the candle alignment attribute. */ - static std::string - normalizeAttributeForSymbol(const dxfcpp::StringLikeWrapper &symbol) { - auto a = MarketEventSymbols::getAttributeStringByKey(symbol, ATTRIBUTE_KEY); - - if (!a) { - return symbol; - } - - try { - auto other = parse(a.value()); - - if (other.get() == DEFAULT) { - return MarketEventSymbols::removeAttributeStringByKey(symbol, ATTRIBUTE_KEY); - } - - if (a.value() != other.get().toString()) { - return MarketEventSymbols::changeAttributeStringByKey(symbol, ATTRIBUTE_KEY, other.get().toString()); - } - - return symbol; - } catch (const InvalidArgumentException &) { - return symbol; - } catch (const std::invalid_argument &) { - return symbol; - } - } + static std::string normalizeAttributeForSymbol(const dxfcpp::StringLikeWrapper &symbol); }; DXFCPP_END_NAMESPACE diff --git a/include/dxfeed_graal_cpp_api/event/candle/CandleSymbolAttribute.hpp b/include/dxfeed_graal_cpp_api/event/candle/CandleSymbolAttribute.hpp index 7943bd62..bcc09f21 100644 --- a/include/dxfeed_graal_cpp_api/event/candle/CandleSymbolAttribute.hpp +++ b/include/dxfeed_graal_cpp_api/event/candle/CandleSymbolAttribute.hpp @@ -11,6 +11,8 @@ DXFCXX_DISABLE_MSC_WARNINGS_PUSH(4251) DXFCPP_BEGIN_NAMESPACE +struct StringLikeWrapper; + /** * Attribute of the CandleSymbol. */ diff --git a/include/dxfeed_graal_cpp_api/internal/Common.hpp b/include/dxfeed_graal_cpp_api/internal/Common.hpp index 342db5bf..c3c08289 100644 --- a/include/dxfeed_graal_cpp_api/internal/Common.hpp +++ b/include/dxfeed_graal_cpp_api/internal/Common.hpp @@ -775,6 +775,7 @@ struct StringLikeWrapper { } }; +/// Universal functional object that allows searching std::unordered_map for string-like keys. struct StringHash { using HashType = std::hash; using is_transparent = void; @@ -783,8 +784,8 @@ struct StringHash { return HashType{}(str); } - std::size_t operator()(std::string_view str) const { - return HashType{}(str); + std::size_t operator()(std::string_view sw) const { + return HashType{}(sw); } std::size_t operator()(std::string const &str) const { diff --git a/src/event/candle/Candle.cpp b/src/event/candle/Candle.cpp index e3214605..773d8a36 100644 --- a/src/event/candle/Candle.cpp +++ b/src/event/candle/Candle.cpp @@ -1,21 +1,20 @@ // Copyright (c) 2024 Devexperts LLC. // SPDX-License-Identifier: MPL-2.0 -#include +#include +#include +#include +#include +#include + +#include #include #include #include #include -#include - -#include - -#include -#include - #include DXFCPP_BEGIN_NAMESPACE diff --git a/src/event/candle/CandleAlignment.cpp b/src/event/candle/CandleAlignment.cpp index 9bf3e3ed..bc9e8abb 100644 --- a/src/event/candle/CandleAlignment.cpp +++ b/src/event/candle/CandleAlignment.cpp @@ -1,10 +1,11 @@ // Copyright (c) 2024 Devexperts LLC. // SPDX-License-Identifier: MPL-2.0 -#include +#include -#include -#include +#include +#include +#include DXFCPP_BEGIN_NAMESPACE @@ -25,4 +26,92 @@ const std::vector> CandleAlignment std::cref(CandleAlignment::SESSION), }; +CandleAlignment::CandleAlignment(const dxfcpp::StringLikeWrapper &string) noexcept : string_{string} { +} + +std::string CandleAlignment::changeAttributeForSymbol(const dxfcpp::StringLikeWrapper &symbol) const { + return *this == DEFAULT ? MarketEventSymbols::removeAttributeStringByKey(symbol, ATTRIBUTE_KEY) + : MarketEventSymbols::changeAttributeStringByKey(symbol, ATTRIBUTE_KEY, toString()); +} + +std::string CandleAlignment::toString() const { + return string_; +} + +bool CandleAlignment::operator==(const CandleAlignment &candleAlignment) const noexcept { + return string_ == candleAlignment.string_; +} + +/** + * Parses string representation of candle alignment into object. + * Any string that was returned by CandleAlignment::toString() can be parsed and case is ignored for parsing. + * + * @param s The string representation of candle alignment. + * @return The candle alignment (reference) + * @throws InvalidArgumentException if the string representation is invalid. + */ +std::reference_wrapper CandleAlignment::parse(const dxfcpp::StringLikeWrapper &s) { + auto found = BY_STRING.find(s); + + if (found != BY_STRING.end()) { + return found->second; + } + + for (const auto &alignmentRef : VALUES) { + const auto &alignmentStr = alignmentRef.get().toString(); + + if (iEquals(alignmentStr, s)) { + return alignmentRef; + } + } + + throw InvalidArgumentException("Unknown candle alignment: " + s); +} + +/** + * Returns candle alignment of the given candle symbol string. + * The result is CandleAlignment::DEFAULT if the symbol does not have candle alignment attribute. + * + * @param symbol The candle symbol string. + * @return candle alignment of the given candle symbol string. + */ +std::reference_wrapper +CandleAlignment::getAttributeForSymbol(const dxfcpp::StringLikeWrapper &symbol) { + auto stringOpt = MarketEventSymbols::getAttributeStringByKey(symbol, ATTRIBUTE_KEY); + + return !stringOpt ? std::cref(DEFAULT) : parse(stringOpt.value()); +} + +/** + * Returns candle symbol string with the normalized representation of the candle alignment attribute. + * + * @param symbol The candle symbol string. + * @return candle symbol string with the normalized representation of the the candle alignment attribute. + */ +std::string CandleAlignment::normalizeAttributeForSymbol(const dxfcpp::StringLikeWrapper &symbol) { + auto a = MarketEventSymbols::getAttributeStringByKey(symbol, ATTRIBUTE_KEY); + + if (!a) { + return symbol; + } + + try { + auto other = parse(a.value()); + + if (other.get() == DEFAULT) { + return MarketEventSymbols::removeAttributeStringByKey(symbol, ATTRIBUTE_KEY); + } + + if (a.value() != other.get().toString()) { + return MarketEventSymbols::changeAttributeStringByKey(symbol, ATTRIBUTE_KEY, other.get().toString()); + } + + return symbol; + } catch (const InvalidArgumentException &) { + return symbol; + } catch (const std::invalid_argument &) { + return symbol; + } +} + DXFCPP_END_NAMESPACE \ No newline at end of file