[text_sensor] Use std::array in SubstituteFilter (#15266)

This commit is contained in:
J. Nick Koston
2026-03-29 14:24:32 -10:00
committed by GitHub
parent 4da7f5ecc2
commit 66754fa376
3 changed files with 21 additions and 19 deletions
+3 -1
View File
@@ -116,7 +116,9 @@ async def substitute_filter_to_code(config, filter_id):
)
for conf in config
]
return cg.new_Pvariable(filter_id, substitutions)
return cg.new_Pvariable(
filter_id, cg.TemplateArguments(len(substitutions)), substitutions
)
@FILTER_REGISTRY.register("map", MapFilter, cv.ensure_list(validate_mapping))
+7 -13
View File
@@ -73,20 +73,14 @@ bool PrependFilter::new_value(std::string &value) {
return true;
}
// Substitute
SubstituteFilter::SubstituteFilter(const std::initializer_list<Substitution> &substitutions)
: substitutions_(substitutions) {}
bool SubstituteFilter::new_value(std::string &value) {
for (const auto &sub : this->substitutions_) {
// Compute lengths once per substitution (strlen is fast, called infrequently)
const size_t from_len = strlen(sub.from);
const size_t to_len = strlen(sub.to);
// Substitute — non-template helper
bool substitute_filter_apply(const Substitution *substitutions, size_t count, std::string &value) {
for (size_t i = 0; i < count; i++) {
const size_t from_len = strlen(substitutions[i].from);
const size_t to_len = strlen(substitutions[i].to);
std::size_t pos = 0;
while ((pos = value.find(sub.from, pos, from_len)) != std::string::npos) {
value.replace(pos, from_len, sub.to, to_len);
// Advance past the replacement to avoid infinite loop when
// the replacement contains the search pattern (e.g., f -> foo)
while ((pos = value.find(substitutions[i].from, pos, from_len)) != std::string::npos) {
value.replace(pos, from_len, substitutions[i].to, to_len);
pos += to_len;
}
}
+11 -5
View File
@@ -123,14 +123,20 @@ struct Substitution {
const char *to;
};
/// A simple filter that replaces a substring with another substring
class SubstituteFilter : public Filter {
/// Non-template helper (implementation in filter.cpp)
bool substitute_filter_apply(const Substitution *substitutions, size_t count, std::string &value);
/// A simple filter that replaces a substring with another substring.
/// N is set by code generation to match the exact number of substitutions configured in YAML.
template<size_t N> class SubstituteFilter : public Filter {
public:
explicit SubstituteFilter(const std::initializer_list<Substitution> &substitutions);
bool new_value(std::string &value) override;
explicit SubstituteFilter(const std::initializer_list<Substitution> &substitutions) {
init_array_from(this->substitutions_, substitutions);
}
bool new_value(std::string &value) override { return substitute_filter_apply(this->substitutions_.data(), N, value); }
protected:
FixedVector<Substitution> substitutions_;
std::array<Substitution, N> substitutions_{};
};
/// Non-template helper (implementation in filter.cpp)