5

I want to get the changes between two given tags, the command is:

git log `Tag1...Tag2 --cherry-pick  --no-merges --right-only

but it is very slow.

I test parameters respectively one by one. ONLY when with --cherry-pick, git log is very slow.

Why? Anybody could help me out there?

qwertzguy
  • 15,699
  • 9
  • 63
  • 66
Bruce Li
  • 173
  • 13

3 Answers3

1

--cherry-pick
Omit any commit that introduces the same change as another commit on the "other side" when the set of commits are limited with symmetric difference.

For example, if you have two branches, A and B, a usual way to list all commits on only one side of them is with --left-right (see the example below in the description of the --left-right option). It however shows the commits that were cherry-picked from the other branch (for example, "3rd on b" may be cherry-picked from branch A). With this option, such pairs of commits are excluded from the output.

It must compare all commits looking for similarities - this will be a very slow operation compared to not having to do any comparison at all.

Shahbaz
  • 46,337
  • 19
  • 116
  • 182
Michael
  • 10,124
  • 1
  • 34
  • 49
  • Thanks for your response, that is right. I see this man page. however , as it said, we are planning to omit the changes which appear on other branch. Do we have some other ways instead of this? – Bruce Li Nov 13 '12 at 03:05
  • If you use merge instead of cherry-pick, you can do this without all the overhead. – Michael Nov 13 '12 at 03:07
  • Yeah, I know, but the problem code base is not our work, we just fetch the changes to analyse the quality of some component. we can't control sw developers' behaviors. – Bruce Li Nov 13 '12 at 05:30
  • A little confuse. I have already pulled repo to local and command above also run at local. what is your meaning? sorry I dont catch you up. – Bruce Li Nov 13 '12 at 06:34
  • Yes.they are from same origin. – Bruce Li Nov 13 '12 at 07:00
0

I've been using

git log tag1 --not tag2

Which gives me all commits on tag1 not on tag2. works fine for branches vs tags as well.

Máté
  • 2,294
  • 3
  • 18
  • 25
-1

Cherry picking could be not so fast, since it's probably detecting renames as part of the merge which can be expensive, especially when you're cherry-picking something which is far away from HEAD.

It may be that your git config has gc.auto = 0 (git config --get gc.auto), so double check if it's enabled, or just run:

git gc

in order to cleanup unnecessary files and optimize the local repository.

You may also try setting the merge.renamelimit config variable to something smaller (e.g. 1, since 0 means no limit). If this won't help, try to profile your git (e.g. using strace or perf record git cherry-pick ...) and find the bottleneck.

See: cherry-pick is slow

For merge-recursive, we would always want to compute the pair-wise renames between each side and the ancestor. So that diff to the cherry-pick destination is always going to be an expensive O(# of changes between source and dest) operation.

Without renames, you could do better on the actual merge with a three-way tree walk. E.g., you see that some sub-tree is at tree A in the ours and ancestor trees, but at tree B in theirs. So you don't have to descend further, and can just say "take theirs" (well, you have to descend theirs to get the values). But I expect it gets more complicated with the interactions with the index (and is probably not worth spending much effort on because of the rename issue, anyway).

-Peff

kenorb
  • 155,785
  • 88
  • 678
  • 743