Skip to content

Commit b8e12ff

Browse files
authored
Fix sort order of weighted transitions if weights are equal (#357)
use stable sort when sorting weighted transitions, respecting the original order
1 parent 27d1a35 commit b8e12ff

File tree

2 files changed

+68
-2
lines changed

2 files changed

+68
-2
lines changed

keyvi/include/keyvi/dictionary/fsa/traversal/weighted_traversal.h

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -69,8 +69,8 @@ inline void TraversalState<WeightedTransition>::Add(uint64_t s, uint32_t weight,
6969
template <>
7070
inline void TraversalState<WeightedTransition>::PostProcess(TraversalPayload<WeightedTransition>* payload) {
7171
if (traversal_state_payload.transitions.size() > 0) {
72-
std::sort(traversal_state_payload.transitions.begin(), traversal_state_payload.transitions.end(),
73-
WeightedTransitionCompare);
72+
std::stable_sort(traversal_state_payload.transitions.begin(), traversal_state_payload.transitions.end(),
73+
WeightedTransitionCompare);
7474
}
7575
}
7676

Lines changed: 66 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,66 @@
1+
//
2+
// keyvi - A key value store.
3+
//
4+
// Copyright 2015 Hendrik Muhs<[email protected]>
5+
//
6+
// Licensed under the Apache License, Version 2.0 (the "License");
7+
// you may not use this file except in compliance with the License.
8+
// You may obtain a copy of the License at
9+
//
10+
// http://www.apache.org/licenses/LICENSE-2.0
11+
//
12+
// Unless required by applicable law or agreed to in writing, software
13+
// distributed under the License is distributed on an "AS IS" BASIS,
14+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15+
// See the License for the specific language governing permissions and
16+
// limitations under the License.
17+
//
18+
19+
/*
20+
* near_traversal.cpp
21+
*
22+
* Created on: Sep 23, 2025
23+
* Author: hendrik
24+
*/
25+
26+
#include <utility>
27+
28+
#include <boost/test/unit_test.hpp>
29+
#include "keyvi/dictionary/fsa/traversal/weighted_traversal.h"
30+
31+
namespace keyvi {
32+
namespace dictionary {
33+
namespace fsa {
34+
namespace traversal {
35+
36+
BOOST_AUTO_TEST_SUITE(WeightedTraversalTests)
37+
38+
BOOST_AUTO_TEST_CASE(PostProcessStableSortEqualWeights) {
39+
TraversalStack<WeightedTransition> traversal_stack;
40+
41+
uint64_t s = 0;
42+
unsigned char c = 97;
43+
44+
// add states with same weights
45+
for (; c < 123; ++c, ++s) {
46+
traversal_stack.traversal_states[0].Add(s, 24, c, &traversal_stack.traversal_stack_payload);
47+
}
48+
49+
// sort by weight (all the same)
50+
traversal_stack.traversal_states[0].PostProcess(&traversal_stack.traversal_stack_payload);
51+
52+
// assert that sort did not change the original order (== stable sort)
53+
c = 97;
54+
for (const auto state : traversal_stack.traversal_states[0].traversal_state_payload.transitions) {
55+
BOOST_CHECK_EQUAL(c++, state.label);
56+
}
57+
58+
BOOST_CHECK_EQUAL(c, 123);
59+
}
60+
61+
BOOST_AUTO_TEST_SUITE_END()
62+
63+
} /* namespace traversal*/
64+
} /* namespace fsa */
65+
} /* namespace dictionary */
66+
} /* namespace keyvi */

0 commit comments

Comments
 (0)