7#include <rapidfuzz/distance/Indel_impl.hpp>
8#include <rapidfuzz/distance/LCSseq.hpp>
17template <
typename InputIt1,
typename InputIt2>
18size_t indel_distance(InputIt1 first1, InputIt1 last1, InputIt2 first2, InputIt2 last2,
19 size_t score_cutoff = std::numeric_limits<size_t>::max())
21 return detail::Indel::distance(first1, last1, first2, last2, score_cutoff, score_cutoff);
24template <
typename Sentence1,
typename Sentence2>
25size_t indel_distance(
const Sentence1& s1,
const Sentence2& s2,
26 size_t score_cutoff = std::numeric_limits<size_t>::max())
28 return detail::Indel::distance(s1, s2, score_cutoff, score_cutoff);
31template <
typename InputIt1,
typename InputIt2>
32size_t indel_similarity(InputIt1 first1, InputIt1 last1, InputIt2 first2, InputIt2 last2,
33 size_t score_cutoff = 0.0)
35 return detail::Indel::similarity(first1, last1, first2, last2, score_cutoff, score_cutoff);
38template <
typename Sentence1,
typename Sentence2>
39size_t indel_similarity(
const Sentence1& s1,
const Sentence2& s2,
size_t score_cutoff = 0.0)
41 return detail::Indel::similarity(s1, s2, score_cutoff, score_cutoff);
44template <
typename InputIt1,
typename InputIt2>
45double indel_normalized_distance(InputIt1 first1, InputIt1 last1, InputIt2 first2, InputIt2 last2,
46 double score_cutoff = 1.0)
48 return detail::Indel::normalized_distance(first1, last1, first2, last2, score_cutoff, score_cutoff);
51template <
typename Sentence1,
typename Sentence2>
52double indel_normalized_distance(
const Sentence1& s1,
const Sentence2& s2,
double score_cutoff = 1.0)
54 return detail::Indel::normalized_distance(s1, s2, score_cutoff, score_cutoff);
57template <
typename InputIt1,
typename InputIt2>
58double indel_normalized_similarity(InputIt1 first1, InputIt1 last1, InputIt2 first2, InputIt2 last2,
59 double score_cutoff = 0.0)
61 return detail::Indel::normalized_similarity(first1, last1, first2, last2, score_cutoff, score_cutoff);
64template <
typename Sentence1,
typename Sentence2>
65double indel_normalized_similarity(
const Sentence1& s1,
const Sentence2& s2,
double score_cutoff = 0.0)
67 return detail::Indel::normalized_similarity(s1, s2, score_cutoff, score_cutoff);
70template <
typename InputIt1,
typename InputIt2>
71Editops indel_editops(InputIt1 first1, InputIt1 last1, InputIt2 first2, InputIt2 last2)
73 return lcs_seq_editops(first1, last1, first2, last2);
76template <
typename Sentence1,
typename Sentence2>
77Editops indel_editops(
const Sentence1& s1,
const Sentence2& s2)
79 return lcs_seq_editops(s1, s2);
83namespace experimental {
86 :
public detail::MultiDistanceBase<MultiIndel<MaxLen>, size_t, 0, std::numeric_limits<int64_t>::max()> {
88 friend detail::MultiDistanceBase<MultiIndel<MaxLen>, size_t, 0, std::numeric_limits<int64_t>::max()>;
89 friend detail::MultiNormalizedMetricBase<MultiIndel<MaxLen>,
size_t>;
92 MultiIndel(
size_t count) : scorer(count)
104 size_t result_count()
const
106 return scorer.result_count();
109 template <
typename Sentence1>
110 void insert(
const Sentence1& s1_)
112 insert(detail::to_begin(s1_), detail::to_end(s1_));
115 template <
typename InputIt1>
116 void insert(InputIt1 first1, InputIt1 last1)
118 scorer.insert(first1, last1);
119 str_lens.push_back(
static_cast<size_t>(std::distance(first1, last1)));
123 template <
typename InputIt2>
124 void _distance(
size_t* scores,
size_t score_count,
const detail::Range<InputIt2>& s2,
125 size_t score_cutoff = std::numeric_limits<size_t>::max())
const
127 scorer.similarity(scores, score_count, s2);
129 for (
size_t i = 0; i < get_input_count(); ++i) {
130 size_t maximum_ = maximum(i, s2);
131 size_t dist = maximum_ - 2 * scores[i];
132 scores[i] = (dist <= score_cutoff) ? dist : score_cutoff + 1;
136 template <
typename InputIt2>
137 size_t maximum(
size_t s1_idx,
const detail::Range<InputIt2>& s2)
const
139 return str_lens[s1_idx] + s2.size();
142 size_t get_input_count() const noexcept
144 return str_lens.size();
147 std::vector<size_t> str_lens;
148 MultiLCSseq<MaxLen> scorer;
153template <
typename CharT1>
155 :
public detail::CachedDistanceBase<CachedIndel<CharT1>, size_t, 0, std::numeric_limits<int64_t>::max()> {
156 template <
typename Sentence1>
157 explicit CachedIndel(
const Sentence1& s1_) : CachedIndel(detail::to_begin(s1_), detail::to_end(s1_))
160 template <
typename InputIt1>
161 CachedIndel(InputIt1 first1, InputIt1 last1)
162 : s1_len(static_cast<size_t>(std::distance(first1, last1))), scorer(first1, last1)
166 friend detail::CachedDistanceBase<CachedIndel<CharT1>, size_t, 0, std::numeric_limits<int64_t>::max()>;
167 friend detail::CachedNormalizedMetricBase<CachedIndel<CharT1>>;
169 template <
typename InputIt2>
170 size_t maximum(
const detail::Range<InputIt2>& s2)
const
172 return s1_len + s2.size();
175 template <
typename InputIt2>
176 size_t _distance(
const detail::Range<InputIt2>& s2,
size_t score_cutoff,
size_t score_hint)
const
178 size_t maximum_ = maximum(s2);
179 size_t lcs_cutoff = (maximum_ / 2 >= score_cutoff) ? maximum_ / 2 - score_cutoff : 0;
180 size_t lcs_cutoff_hint = (maximum_ / 2 >= score_hint) ? maximum_ / 2 - score_hint : 0;
181 size_t lcs_sim = scorer.similarity(s2, lcs_cutoff, lcs_cutoff_hint);
182 size_t dist = maximum_ - 2 * lcs_sim;
183 return (dist <= score_cutoff) ? dist : score_cutoff + 1;
187 CachedLCSseq<CharT1> scorer;
190#ifdef RAPIDFUZZ_DEDUCTION_GUIDES
191template <
typename Sentence1>
192explicit CachedIndel(
const Sentence1& s1_) -> CachedIndel<char_type<Sentence1>>;
194template <
typename InputIt1>
195CachedIndel(InputIt1 first1, InputIt1 last1) -> CachedIndel<iter_value_t<InputIt1>>;