Mercurial > hg > mercurial-source
changeset 33583:3e6f9bff7e3f
revset: filter first/last members by __and__ operation
This replaces 'if y in subset' with '& subset'. first(null) and last(wdir())
are fixed thanks to fullreposet.__and__.
This also revealed that first() and last() don't follow the order of the
input set. 'ls & subset' is valid only if the ordering requirement is 'define'
or 'any'.
No performance regression observed:
revset #0: limit(0:9999, 100, 9000)
0) 0.001164
1) 0.001135
revset #2: 9000 & limit(0:9999, 100, 9000)
0) 0.001224
1) 0.001181
revset #3: last(0:9999, 100)
0) 0.000237
1) 0.000199
author | Yuya Nishihara <yuya@tcha.org> |
---|---|
date | Sat, 10 Jun 2017 19:41:42 +0900 |
parents | b36ec65ea583 |
children | 348b491c0934 |
files | mercurial/revset.py tests/test-revset.t |
diffstat | 2 files changed, 61 insertions(+), 20 deletions(-) [+] |
line wrap: on
line diff
--- a/mercurial/revset.py +++ b/mercurial/revset.py @@ -1179,10 +1179,9 @@ y = next(it, None) if y is None: break - elif y in subset: - result.append(y) - return baseset(result, datarepr=('<limit n=%d, offset=%d, %r, %r>', - lim, ofs, subset, os)) + result.append(y) + ls = baseset(result, datarepr=('<limit n=%d, offset=%d, %r>', lim, ofs, os)) + return ls & subset @predicate('last(set, [n])', safe=True) def last(repo, subset, x): @@ -1204,10 +1203,10 @@ y = next(it, None) if y is None: break - elif y in subset: - result.append(y) - return baseset(result[::-1], datarepr=('<last n=%d, %r, %r>', - lim, subset, os)) + result.append(y) + ls = baseset(result, datarepr=('<last n=%d, %r>', lim, os)) + ls.reverse() + return ls & subset @predicate('max(set)', safe=True) def maxrev(repo, subset, x):
--- a/tests/test-revset.t +++ b/tests/test-revset.t @@ -1016,6 +1016,50 @@ 8 9 +Test order of first/last revisions + + $ hg debugrevspec -s 'first(4:0, 3) & 3:' + * set: + <filteredset + <baseset + <limit n=3, offset=0, + <spanset- 0:4>>>, + <spanset+ 3:9>> + 4 + 3 + + $ hg debugrevspec -s '3: & first(4:0, 3)' + * set: + <filteredset + <baseset + <limit n=3, offset=0, + <spanset- 0:4>>>, + <spanset+ 3:9>> + 4 + 3 +BROKEN: should be '3 4' + + $ hg debugrevspec -s 'last(4:0, 3) & :1' + * set: + <filteredset + <baseset + <last n=3, + <spanset+ 0:4>>>, + <spanset+ 0:1>> + 1 + 0 + + $ hg debugrevspec -s ':1 & last(4:0, 3)' + * set: + <filteredset + <baseset + <last n=3, + <spanset+ 0:4>>>, + <spanset+ 0:1>> + 1 + 0 +BROKEN: should be '0 1' + Test matching $ log 'matching(6)' @@ -1230,10 +1274,10 @@ $ log 'reverse(null:)' | tail -2 0 -1 + $ log 'first(null:)' + -1 + $ log 'min(null:)' BROKEN: should be '-1' - $ log 'first(null:)' -BROKEN: should be '-1' - $ log 'min(null:)' $ log 'tip:null and all()' | tail -2 1 0 @@ -1295,9 +1339,9 @@ 9 $ log '(all() + wdir()) & max(. + wdir())' 2147483647 - $ log '(all() + wdir()) & first(wdir() + .)' + $ log 'first(wdir() + .)' 2147483647 - $ log '(all() + wdir()) & last(. + wdir())' + $ log 'last(. + wdir())' 2147483647 Test working-directory integer revision and node id @@ -1907,10 +1951,11 @@ follow) define) * set: - <baseset - <limit n=1, offset=0, - <spanset- 0:2>, - <baseset [1, 0, 2]>>> + <filteredset + <baseset + <limit n=1, offset=0, + <baseset [1, 0, 2]>>>, + <spanset- 0:2>> 1 $ try --optimize '2:0 & not last(0 + 2 + 1)' @@ -1946,7 +1991,6 @@ <not <baseset <last n=1, - <fullreposet+ 0:9>, <baseset [1, 2, 0]>>>>> 2 0 @@ -3573,7 +3617,6 @@ <filteredset <baseset <limit n=2, offset=0, - <fullreposet+ 0:9>, <baseset [1, 2, 3]>>>, <not <baseset [2]>>> @@ -3630,7 +3673,6 @@ <filteredset <baseset <last n=1, - <fullreposet+ 0:9>, <baseset [2, 1]>>>, <not <baseset [2]>>>