← Index
NYTProf Performance Profile   « block view • line view • sub view »
For /usr/local/src/github.com/foswiki/core/bin/view
  Run on Sun Dec 4 17:17:59 2011
Reported on Sun Dec 4 17:26:35 2011

Filename/usr/local/src/github.com/foswiki/core/lib/Foswiki/Search/ResultSet.pm
StatementsExecuted 408 statements in 3.09ms
Subroutines
Calls P F Exclusive
Time
Inclusive
Time
Subroutine
45221.02ms2.14msFoswiki::Search::ResultSet::::hasNextFoswiki::Search::ResultSet::hasNext
2211358µs471µsFoswiki::Search::ResultSet::::nextFoswiki::Search::ResultSet::next
11147µs47µsFoswiki::Search::ResultSet::::newFoswiki::Search::ResultSet::new
11128µs38µsFoswiki::Search::ResultSet::::BEGIN@17Foswiki::Search::ResultSet::BEGIN@17
11128µs34µsFoswiki::Search::ResultSet::::sortResultsFoswiki::Search::ResultSet::sortResults
11119µs42µsFoswiki::Search::ResultSet::::BEGIN@18Foswiki::Search::ResultSet::BEGIN@18
11118µs62µsFoswiki::Search::ResultSet::::BEGIN@24Foswiki::Search::ResultSet::BEGIN@24
11117µs17µsFoswiki::Search::ResultSet::::BEGIN@23Foswiki::Search::ResultSet::BEGIN@23
11110µs10µsFoswiki::Search::ResultSet::::BEGIN@20Foswiki::Search::ResultSet::BEGIN@20
0000s0sFoswiki::Search::ResultSet::::filterByDateFoswiki::Search::ResultSet::filterByDate
0000s0sFoswiki::Search::ResultSet::::nextWebFoswiki::Search::ResultSet::nextWeb
0000s0sFoswiki::Search::ResultSet::::numberOfTopicsFoswiki::Search::ResultSet::numberOfTopics
0000s0sFoswiki::Search::ResultSet::::skipFoswiki::Search::ResultSet::skip
Call graph for these subroutines as a Graphviz dot language file.
Line State
ments
Time
on line
Calls Time
in subs
Code
1# See bottom of file for license and copyright information
2
3=begin TML
4
5---+ package Foswiki::Search::ResultSet
6
7This class implements the ResultSet API - its basically a Sorted Aggregate Iterator for foswiki 1.1
8 * NOTE: does not implement the unique function - by its nature, the data is unique, and it would be a non-trivial drain on memory in this context
9
10(due to the partially completed InfoCache removeal)
11
12in future it will probably become more clever.
13
14=cut
15
16package Foswiki::Search::ResultSet;
17248µs248µs
# spent 38µs (28+10) within Foswiki::Search::ResultSet::BEGIN@17 which was called: # once (28µs+10µs) by Foswiki::Search::BEGIN@20 at line 17
use strict;
# spent 38µs making 1 call to Foswiki::Search::ResultSet::BEGIN@17 # spent 10µs making 1 call to strict::import
18246µs265µs
# spent 42µs (19+23) within Foswiki::Search::ResultSet::BEGIN@18 which was called: # once (19µs+23µs) by Foswiki::Search::BEGIN@20 at line 18
use warnings;
# spent 42µs making 1 call to Foswiki::Search::ResultSet::BEGIN@18 # spent 23µs making 1 call to warnings::import
19
20271µs110µs
# spent 10µs within Foswiki::Search::ResultSet::BEGIN@20 which was called: # once (10µs+0s) by Foswiki::Search::BEGIN@20 at line 20
use Foswiki::Iterator ();
# spent 10µs making 1 call to Foswiki::Search::ResultSet::BEGIN@20
21110µsour @ISA = ('Foswiki::Iterator');
22
23250µs117µs
# spent 17µs within Foswiki::Search::ResultSet::BEGIN@23 which was called: # once (17µs+0s) by Foswiki::Search::BEGIN@20 at line 23
use Foswiki::Search::InfoCache;
# spent 17µs making 1 call to Foswiki::Search::ResultSet::BEGIN@23
2421.41ms2106µs
# spent 62µs (18+44) within Foswiki::Search::ResultSet::BEGIN@24 which was called: # once (18µs+44µs) by Foswiki::Search::BEGIN@20 at line 24
use Assert;
# spent 62µs making 1 call to Foswiki::Search::ResultSet::BEGIN@24 # spent 44µs making 1 call to Assert::import
25
26=begin TML
27
28---++ new(\@list)
29
30Create a new iterator over the given list of iterators. The list is
31not damaged in any way.
32
33=cut
34
35
# spent 47µs within Foswiki::Search::ResultSet::new which was called: # once (47µs+0s) by Foswiki::Store::Interfaces::QueryAlgorithm::query at line 122 of /usr/local/src/github.com/foswiki/core/lib/Foswiki/Store/Interfaces/QueryAlgorithm.pm
sub new {
36349µs my ( $class, $list, $partition, $sortby, $revSort ) = @_;
37
38 my $this = bless(
39 {
40 Itr_list => $list,
41 Itr_index => 0,
42 next => undef,
43 Itr_next => [],
44 partition => $partition || 'web',
45 sortby => $sortby || 'topic',
46 revsort => $revSort || 0,
47 },
48 $class
49 );
50
51 return $this;
52}
53
54sub numberOfTopics {
55 my $this = shift;
56
57 return $this->{count} if ( defined( $this->{count} ) );
58
59 my $count = 0;
60 foreach my $infocache ( @{ $this->{Itr_list} } ) {
61 $count += $infocache->numberOfTopics();
62 }
63 $this->{count} = $count;
64
65 return $count;
66}
67
68=begin TML
69
70---++ hasNext() -> $boolean
71
72Returns false when the iterator is exhausted.
73
74=cut
75
76
# spent 2.14ms (1.02+1.11) within Foswiki::Search::ResultSet::hasNext which was called 45 times, avg 47µs/call: # 23 times (911µs+1.11ms) by Foswiki::Iterator::FilterIterator::hasNext at line 64 of /usr/local/src/github.com/foswiki/core/lib/Foswiki/Iterator/FilterIterator.pm, avg 88µs/call # 22 times (113µs+0s) by Foswiki::Search::ResultSet::next at line 228, avg 5µs/call
sub hasNext {
772791.02ms my ($this) = @_;
78 return 1 if $this->{next};
79
80#this is the 'normal' legacy way to iterate over the list of results (one web at a time)
81 if (
82 ( $this->{partition} eq 'web' )
83 or (
84 scalar( @{ $this->{Itr_list} } ) <= 0
85 ) #no reason to got through the more complex case if there's only one itr
86 )
87 {
88 my $n;
89 do {
90 unless ( $this->{list} ) {
91 if ( $this->{Itr_index} < scalar( @{ $this->{Itr_list} } ) ) {
92 $this->{list} = $this->{Itr_list}->[ $this->{Itr_index}++ ];
93 }
94 else {
95 return 0; #no more iterators in list
96 }
97 }
9823586µs if ( $this->{list}->hasNext() ) {
# spent 586µs making 23 calls to Foswiki::ListIterator::hasNext, avg 25µs/call
9922525µs $n = $this->{list}->next();
# spent 525µs making 22 calls to Foswiki::ListIterator::next, avg 24µs/call
100 }
101 else {
102 $this->{list} = undef; #goto next iterator
103 }
104 } while ( !$this->{list} );
105 $this->{next} = $n;
106 }
107 else {
108
109#yes, this is innefficient, for now I'm looking only to get a functioning result.
110 my $next = -1;
111 for ( my $idx = 0 ; $idx < scalar( @{ $this->{Itr_list} } ) ; $idx++ ) {
112
113 #load the next element from each of the iterators
114 if ( !defined( $this->{Itr_next}[$idx] )
115 and $this->{Itr_list}[$idx]->hasNext() )
116 {
117 $this->{Itr_next}[$idx] = $this->{Itr_list}[$idx]->next();
118 }
119 if ( defined( $this->{Itr_next}[$idx] ) ) {
120
121 #find the first one of them (works because each iterator is already sorted..
122 if ( $next == -1 ) {
123 $next = $idx;
124 next;
125 }
126
127 #print STDERR "------ trying ($idx) ".$this->{Itr_next}[$idx]."\n";
128 #compare $next's elem with $idx's and rotate if needed
129 my @two = ( $this->{Itr_next}[$next], $this->{Itr_next}[$idx] );
130 Foswiki::Search::InfoCache::sortTopics( \@two, $this->{sortby},
131 !$this->{revsort} );
132 if ( $two[0] ne $this->{Itr_next}[$next] ) {
133 $next = $idx;
134 }
135 }
136 }
137
138 #print STDERR "---getting result from $next\n";
139 if ( $next == -1 ) {
140 return 0;
141 }
142 else {
143 $this->{next} = $this->{Itr_next}[$next];
144 $this->{Itr_next}[$next] = undef;
145 }
146
147 }
148 return 1;
149}
150
151=begin TML
152
153---++ skip(count) -> $countremaining
154
155skip X elements (returns 0 if successful, or number of elements remaining to skip if there are not enough elements to skip)
156skip must set up next as though hasNext was called.
157
158=cut
159
160sub skip {
161 my $this = shift;
162 my $count = shift;
163
164 return 0 if ( $count <= 0 );
165 print STDERR
166 "--------------------------------------------ResultSet::skip($count)\n"
167 if Foswiki::Iterator::MONITOR;
168
169 #ask CAN skip() for faster path
170 if (
171 (
172 ( $this->{partition} eq 'web' )
173 or ( scalar( @{ $this->{Itr_list} } ) == 0 )
174 )
175 and #no reason to got through the more complex case if there's only one itr
176 ( $this->{Itr_list}->[0]->can('skip')
177 ) #nasty assumption that all the itr's are a similar type (that happens to be true)
178 )
179 {
180 if ( not defined( $this->{list} ) ) {
181 $this->{list} = $this->{Itr_list}->[ $this->{Itr_index}++ ];
182 }
183 while ( $count > 0 ) {
184 return $count if ( not defined( $this->{list} ) );
185 $count = $this->{list}->skip($count);
186 $this->{next} = $this->{list}->{next};
187 if ( $count > 0 ) {
188 $this->{list} = $this->{Itr_list}->[ $this->{Itr_index}++ ];
189 $this->{next} = undef;
190 }
191 }
192 }
193 else {
194
195 #brute force -
196 while (
197 ( $count > 0
198 ) #must come first - don't want to advance the inner itr if count ==0
199 and $this->hasNext()
200 )
201 {
202 $count--;
203 $this->next(); #drain next, so hasNext goes to next element
204 }
205 }
206
207 if ( $count >= 0 ) {
208
209 #finished.
210 $this->{next} = undef;
211 }
212 print STDERR
213"--------------------------------------------ResultSet::skip() => $count\n"
214 if Foswiki::Iterator::MONITOR;
215 return $count;
216}
217
218=begin TML
219
220---++ next() -> $data
221
222Return the next entry in the list.
223
224=cut
225
226
# spent 471µs (358+113) within Foswiki::Search::ResultSet::next which was called 22 times, avg 21µs/call: # 22 times (358µs+113µs) by Foswiki::Iterator::FilterIterator::hasNext at line 65 of /usr/local/src/github.com/foswiki/core/lib/Foswiki/Iterator/FilterIterator.pm, avg 21µs/call
sub next {
227110354µs my $this = shift;
22822113µs $this->hasNext();
# spent 113µs making 22 calls to Foswiki::Search::ResultSet::hasNext, avg 5µs/call
229 my $n = $this->{next};
230 $this->{next} = undef;
231
232 return $n;
233}
234
235=begin TML
236
237---++ nextWeb() -> $data
238
239switch tot he next Web (only works on partition==web, and if we've already started iterating.
240=cut
241
242sub nextWeb {
243 my $this = shift;
244
245 ASSERT( $this->{partition} eq 'web' ) if DEBUG;
246 ASSERT( $this->{list} ) if DEBUG;
247
248 $this->{list} = undef;
249 $this->hasNext();
250}
251
252=begin TML
253---++ sortResults
254
255the implementation of %SORT{"" limit="" order="" reverse="" date=""}%
256
257it should be possible for the search engine to pre-sort, making this a nop, or to
258delay evaluated, partially evaluated, or even delegated to the DB/SQL
259
260=cut
261
262
# spent 34µs (28+6) within Foswiki::Search::ResultSet::sortResults which was called: # once (28µs+6µs) by Foswiki::Store::Interfaces::QueryAlgorithm::query at line 130 of /usr/local/src/github.com/foswiki/core/lib/Foswiki/Store/Interfaces/QueryAlgorithm.pm
sub sortResults {
263428µs my ( $this, $params ) = @_;
264
265 foreach my $infocache ( @{ $this->{Itr_list} } ) {
26617µs $infocache->sortResults($params);
# spent 7µs making 1 call to Foswiki::Search::InfoCache::sortResults
267 }
268}
269
270sub filterByDate {
271 my ( $this, $date ) = @_;
272
273 foreach my $infocache ( @{ $this->{Itr_list} } ) {
274 $infocache->filterByDate($date);
275 }
276}
277
27816µs1;
279__END__