2 * @brief Class representing a list of query expansion terms
4 /* Copyright (C) 2015,2016,2017 Olly Betts
6 * This program is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU General Public License as
8 * published by the Free Software Foundation; either version 2 of the
9 * License, or (at your option) any later version.
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301
22 #ifndef XAPIAN_INCLUDED_ESET_H
23 #define XAPIAN_INCLUDED_ESET_H
25 #if !defined XAPIAN_IN_XAPIAN_H && !defined XAPIAN_LIB_BUILD
26 # error "Never use <xapian/eset.h> directly; include <xapian.h> instead."
32 #include <xapian/attributes.h>
33 #include <xapian/intrusive_ptr.h>
34 #include <xapian/stem.h>
35 #include <xapian/types.h>
36 #include <xapian/visibility.h>
42 /// Class representing a list of search results.
43 class XAPIAN_VISIBILITY_DEFAULT ESet
{
44 friend class ESetIterator
;
47 /// Class representing the ESet internals.
49 /// @private @internal Reference counted internals.
50 Xapian::Internal::intrusive_ptr_nonnull
<Internal
> internal
;
52 /** Copying is allowed.
54 * The internals are reference counted, so copying is cheap.
58 /** Copying is allowed.
60 * The internals are reference counted, so assignment is cheap.
62 ESet
& operator=(const ESet
& o
);
64 /** Default constructor.
66 * Creates an empty ESet, mostly useful as a placeholder.
73 /** Return number of items in this ESet object. */
74 Xapian::doccount
size() const;
76 /** Return true if this ESet object is empty. */
77 bool empty() const { return size() == 0; }
79 /** Return a bound on the full size of this ESet object.
81 * This is a bound on size() if get_eset() had been called with
82 * maxitems set high enough that all results were returned.
84 Xapian::termcount
get_ebound() const;
86 /** Efficiently swap this ESet object with another. */
87 void swap(ESet
& o
) { internal
.swap(o
.internal
); }
89 /** Return iterator pointing to the first item in this ESet. */
90 ESetIterator
begin() const;
92 /** Return iterator pointing to just after the last item in this ESet. */
93 ESetIterator
end() const;
95 /** Return iterator pointing to the i-th object in this ESet. */
96 ESetIterator
operator[](Xapian::doccount i
) const;
98 /** Return iterator pointing to the last object in this ESet. */
99 ESetIterator
back() const;
101 /// Return a string describing this object.
102 std::string
get_description() const;
104 /** @private @internal ESet is what the C++ STL calls a container.
106 * The following typedefs allow the class to be used in templates in the
107 * same way the standard containers can be.
109 * These are deliberately hidden from the Doxygen-generated docs, as the
110 * machinery here isn't interesting to API users. They just need to know
111 * that Xapian container classes are compatible with the STL.
113 * See "The C++ Programming Language", 3rd ed. section 16.3.1:
117 typedef Xapian::ESetIterator value_type
;
119 typedef Xapian::termcount size_type
;
121 typedef Xapian::termcount_diff difference_type
;
123 typedef Xapian::ESetIterator iterator
;
125 typedef Xapian::ESetIterator const_iterator
;
127 typedef value_type
* pointer
;
129 typedef const value_type
* const_pointer
;
131 typedef value_type
& reference
;
133 typedef const value_type
& const_reference
;
136 /** @private @internal ESet is what the C++ STL calls a container.
138 * The following methods allow the class to be used in templates in the
139 * same way the standard containers can be.
141 * These are deliberately hidden from the Doxygen-generated docs, as the
142 * machinery here isn't interesting to API users. They just need to know
143 * that Xapian container classes are compatible with the STL.
146 // The size is fixed once created.
147 Xapian::doccount
max_size() const { return size(); }
151 /// Iterator over a Xapian::ESet.
152 class XAPIAN_VISIBILITY_DEFAULT ESetIterator
{
155 ESetIterator(const Xapian::ESet
& eset_
, Xapian::doccount off_from_end_
)
156 : eset(eset_
), off_from_end(off_from_end_
) { }
159 /** @private @internal The ESet we are iterating over. */
162 /** @private @internal The current position of the iterator.
164 * We store the offset from the end of @a eset, since that means
165 * ESet::end() just needs to set this member to 0.
167 Xapian::ESet::size_type off_from_end
;
169 /** Create an unpositioned ESetIterator. */
170 ESetIterator() : off_from_end(0) { }
172 /** Get the term at the current position. */
173 std::string
operator*() const;
175 /// Advance the iterator to the next position.
176 ESetIterator
& operator++() {
181 /// Advance the iterator to the next position (postfix version).
182 ESetIterator
operator++(int) {
183 ESetIterator retval
= *this;
188 /// Move the iterator to the previous position.
189 ESetIterator
& operator--() {
194 /// Move the iterator to the previous position (postfix version).
195 ESetIterator
operator--(int) {
196 ESetIterator retval
= *this;
201 /** @private @internal ESetIterator is what the C++ STL calls an
202 * random_access_iterator.
204 * The following typedefs allow std::iterator_traits<> to work so that
205 * this iterator can be used with the STL.
207 * These are deliberately hidden from the Doxygen-generated docs, as the
208 * machinery here isn't interesting to API users. They just need to know
209 * that Xapian iterator classes are compatible with the STL.
213 typedef std::random_access_iterator_tag iterator_category
;
215 typedef std::string value_type
;
217 typedef Xapian::termcount_diff difference_type
;
219 typedef std::string
* pointer
;
221 typedef std::string
& reference
;
224 /// Move the iterator forwards by n positions.
225 ESetIterator
& operator+=(difference_type n
) {
230 /// Move the iterator back by n positions.
231 ESetIterator
& operator-=(difference_type n
) {
236 /** Return the iterator incremented by @a n positions.
238 * If @a n is negative, decrements by (-n) positions.
240 ESetIterator
operator+(difference_type n
) const {
241 return ESetIterator(eset
, off_from_end
- n
);
244 /** Return the iterator decremented by @a n positions.
246 * If @a n is negative, increments by (-n) positions.
248 ESetIterator
operator-(difference_type n
) const {
249 return ESetIterator(eset
, off_from_end
+ n
);
252 /** Return the number of positions between @a o and this iterator. */
253 difference_type
operator-(const ESetIterator
& o
) const {
254 return difference_type(o
.off_from_end
) - difference_type(off_from_end
);
257 /** Get the weight for the current position. */
258 double get_weight() const;
260 /// Return a string describing this object.
261 std::string
get_description() const;
265 XAPIAN_NOTHROW(operator==(const ESetIterator
&a
, const ESetIterator
&b
));
267 /// Equality test for ESetIterator objects.
269 operator==(const ESetIterator
&a
, const ESetIterator
&b
) XAPIAN_NOEXCEPT
271 return a
.off_from_end
== b
.off_from_end
;
275 XAPIAN_NOTHROW(operator!=(const ESetIterator
&a
, const ESetIterator
&b
));
277 /// Inequality test for ESetIterator objects.
279 operator!=(const ESetIterator
&a
, const ESetIterator
&b
) XAPIAN_NOEXCEPT
285 XAPIAN_NOTHROW(operator<(const ESetIterator
&a
, const ESetIterator
&b
));
287 /// Inequality test for ESetIterator objects.
289 operator<(const ESetIterator
&a
, const ESetIterator
&b
) XAPIAN_NOEXCEPT
291 return a
.off_from_end
> b
.off_from_end
;
295 XAPIAN_NOTHROW(operator>(const ESetIterator
&a
, const ESetIterator
&b
));
297 /// Inequality test for ESetIterator objects.
299 operator>(const ESetIterator
&a
, const ESetIterator
&b
) XAPIAN_NOEXCEPT
305 XAPIAN_NOTHROW(operator>=(const ESetIterator
&a
, const ESetIterator
&b
));
307 /// Inequality test for ESetIterator objects.
309 operator>=(const ESetIterator
&a
, const ESetIterator
&b
) XAPIAN_NOEXCEPT
315 XAPIAN_NOTHROW(operator<=(const ESetIterator
&a
, const ESetIterator
&b
));
317 /// Inequality test for ESetIterator objects.
319 operator<=(const ESetIterator
&a
, const ESetIterator
&b
) XAPIAN_NOEXCEPT
324 /** Return ESetIterator @a it incremented by @a n positions.
326 * If @a n is negative, decrements by (-n) positions.
329 operator+(ESetIterator::difference_type n
, const ESetIterator
& it
)
334 // Inlined methods of ESet which need ESetIterator to have been defined:
337 ESet::begin() const {
338 return ESetIterator(*this, size());
343 // Decrementing the result of end() needs to work, so we must pass in
345 return ESetIterator(*this, 0);
349 ESet::operator[](Xapian::doccount i
) const {
350 return ESetIterator(*this, size() - i
);
355 return ESetIterator(*this, 1);
360 #endif // XAPIAN_INCLUDED_ESET_H