SWAP_HRD - Swap (Hard - Level 1000)


Let's play with sequence of non negative integer. Given two sequence of n non negative integers (a1, a2 ... an) and (b1, b2 ... bn). Both sequence has maximum element less than k, max(a1, a2 ... an) < k and max(b1, b2 ... bn) < k. The game rule is you can edit both sequence with this operation: swap ai and bi with 1 ≤ in, and the goal is to make sequence a and b become increasing sequence: ai ≤ aj if and only if ij and bi ≤ bj if and only if ij. But not all initial sequence a and b can be solved.

For example (2, 0) and (0, 1) is a pair of sequence that can't be solved:

  • If you don't swap any element, you have (2, 0) and (0, 1), but sequence (2, 0) is not increasing.
  • If you swap first element only, then the pair become like this (0, 0) and (2, 1), sequence (2, 1) is not increasing.
  • If you swap second element only, then the pair become like this (2, 1) and (0, 0), again (2, 1) is not increasing.
  • If you swap both element, then the pair become like this (0, 1) and (2, 0), again (2, 0) is not increasing

So it's impossible to solve if initial sequence is (2, 0) and (0, 1), because all possible move can't make both sequence become increasing.

Now given n and k, your task is to compute number of different pair of initial sequence (a, b) that can be solved with game described above.

Input

First line there is an integer T denoting number of test case, then T test cases follow.

For each case, there are two integers n and k written in one line, separated by a space.

Output

For each case, output number of different pair of initial sequence (a, b), since the answer can be large, output the answer modulo 109+7.

Constraints

0 < T ≤ 104

0 < min(n, k) ≤ 1000

0 < max(n, k) < 101000

Example

Input:
6
2 1
1 2
1 3
2 2
3 2
2 3

Output:
1
4
9
11
26
46

Explanation

Here is list of all possible pair of initial sequence (a, b) on each case:

Case 1: {[(0, 0), (0, 0)]}

Case 2: {[(0), (0)], [(0), (1)], [(1), (0)], [(1), (1)]}

Case 3: {[(0), (0)], [(0), (1)], [(0), (2)], [(1), (0)], [(1), (1)], [(1), (2)], [(2), (0)], [(2), (1)], [(2), (2)]}

Case 4: {[(0, 0), (0, 0)], [(0, 0), (0, 1)], [(0, 0), (1, 1)], [(0, 1), (0, 0)], [(0, 1), (0, 1)], [(0, 1), (1, 0)], [(0, 1), (1, 1)], [(1, 0), (0, 1)], [(1, 1), (0, 0)], [(1, 1), (0, 1)], [(1, 1), (1, 1)]}

Case 5: {[(0, 0, 0), (0, 0, 0)], [(0, 0, 0), (0, 0, 1)], [(0, 0, 0), (0, 1, 1)], [(0, 0, 0), (1, 1, 1)], [(0, 0, 1), (0, 0, 0)], [(0, 0, 1), (0, 0, 1)], [(0, 0, 1), (0, 1, 0)], [(0, 0, 1), (0, 1, 1)], [(0, 0, 1), (1, 1, 0)], [(0, 0, 1), (1, 1, 1)], [(0, 1, 0), (0, 0, 1)], [(0, 1, 0), (1, 0, 1)], [(0, 1, 1), (0, 0, 0)], [(0, 1, 1), (0, 0, 1)], [(0, 1, 1), (0, 1, 1)], [(0, 1, 1), (1, 0, 0)], [(0, 1, 1), (1, 0, 1)], [(0, 1, 1), (1, 1, 1)], [(1, 0, 0), (0, 1, 1)], [(1, 0, 1), (0, 1, 0)], [(1, 0, 1), (0, 1, 1)], [(1, 1, 0), (0, 0, 1)], [(1, 1, 1), (0, 0, 0)], [(1, 1, 1), (0, 0, 1)], [(1, 1, 1), (0, 1, 1)], [(1, 1, 1), (1, 1, 1)]}

Case 6: {[(0, 0), (0, 0)], [(0, 0), (0, 1)], [(0, 0), (0, 2)], [(0, 0), (1, 1)], [(0, 0), (1, 2)], [(0, 0), (2, 2)], [(0, 1), (0, 0)], [(0, 1), (0, 1)], [(0, 1), (0, 2)], [(0, 1), (1, 0)], [(0, 1), (1, 1)], [(0, 1), (1, 2)], [(0, 1), (2, 2)], [(0, 2), (0, 0)], [(0, 2), (0, 1)], [(0, 2), (0, 2)], [(0, 2), (1, 0)], [(0, 2), (1, 1)], [(0, 2), (1, 2)], [(0, 2), (2, 0)], [(0, 2), (2, 1)], [(0, 2), (2, 2)], [(1, 0), (0, 1)], [(1, 0), (0, 2)], [(1, 1), (0, 0)], [(1, 1), (0, 1)], [(1, 1), (0, 2)], [(1, 1), (1, 1)], [(1, 1), (1, 2)], [(1, 1), (2, 2)], [(1, 2), (0, 0)], [(1, 2), (0, 1)], [(1, 2), (0, 2)], [(1, 2), (1, 1)], [(1, 2), (1, 2)], [(1, 2), (2, 1)], [(1, 2), (2, 2)], [(2, 0), (0, 2)], [(2, 1), (0, 2)], [(2, 1), (1, 2)], [(2, 2), (0, 0)], [(2, 2), (0, 1)], [(2, 2), (0, 2)], [(2, 2), (1, 1)], [(2, 2), (1, 2)], [(2, 2), (2, 2)]}

Other Info

Test case (n and k) is generated randomly using this rule:

  • Probability that n>k or n<=k is ~50% each.
  • Maximum n and k is random log-uniform.
  • Minimum n and k is random uniform.

Click here if you want to know my program speed and other detail.

Explanation about my Algorithm complexity:

My 3.8KB of C code with O(min(n, k)^3) complexity got AC in 32.17s.

Other submission like O(min(n, k)^4) in fast language, and O(min(n, k)^3) in slow language is all TLE. That's why this problem has "Hard" label.

Sorry for slow language user, I think it's impossible to solve this problem unless O(min(n, k)^2) exists. I recommend to try Medium version first, or learn fast language :-P

About complexity, I've proved using math that no algorithm with complexity better than O(min(n, k)^2), this is the lower bound. My best algorithm for now is O(min(n, k)^3), this is the upper bound. So the optimal algorithm lies between that lower and upper bound. I still don't have proof that my algo is optimal, so there is possibility that there is an algorithm that better than O(min(n, k)^3).

Btw, if I found around O(min(n, k)^2) by myself, I'll set "Extreme" version (level 10000+) of this problem. But if there is someone who solve this problem in around O(min(n, k)^2), of course he/she has honor to set "Extreme" version of this problem.

Time limit ~3× my program top speed.


See also: Another problem added by Tjandra Satria Gunawan


hide comments
Min_25: 2018-05-06 07:36:05

@Blue.Mary
Except for the cases where n ≡ -1 (mod 10^9 + 7) with small K, which are fortunately not included, my solution can indeed solve the problem in O(min{N + log K, K + log(N)}) time without any initialization or pre-computation. So, my solution works even if min{N, K} <= 10^7 except for the above cases.

Last edit: 2018-05-06 08:09:18
[Rampage] Blue.Mary: 2018-05-06 06:26:02

For time complexity, Min_25 and the problem author doesn't talk about the same thing, which may confuse the other problems solvers. The problem author actually means "the time complexity of initialization", while min_25 actually means "the time complexity to solve all test cases AFTER initialization". Nevertheless, the initialization can actually be done offline (and use carefully prepared constant table in program), so the super long time limit is NOT necessary.

For other problem solvers' information, my program (which doesn't use constant table in program) uses about 21.4 sec to initialize, and solves all test cases in about 0.4 sec.

(If min_25's last comment is correct, then the note in problem description should be completely deleted. It's very misleading.)

Last edit: 2018-05-07 05:42:05
Min_25: 2016-05-02 07:17:20

Now, I have an O(T * min(N + log(K), K + log(N)) solution. ;-)

(Tjandra Satria Gunawan)(曾毅昆): 2014-05-27 18:47:29

@Min_25: Thanks and congratulations, your program running time is the fastest and your code is easy to read (thanks for the comment on your code).
I hope many users can enjoy this problem. Although it's not 100% my problem.

Min_25: 2014-05-26 16:43:04

Very beautiful problem.
Many famous sequences appeared.

EDIT:
My Python code got AC ! :)

Last edit: 2014-05-28 08:30:25
(Tjandra Satria Gunawan)(曾毅昆): 2013-06-24 01:54:47

Congratulations to Robert Gerbicz who solve this hard problem less than one day.
----
(for comparsion, I need about 10 days to build O(min(n,k)^4) + 4 days to build O(min(n,k)^3))..

(Tjandra Satria Gunawan)(曾毅昆): 2013-06-23 13:51:45

in my opinion this is the hardest problem I ever publish on SPOJ (Because need deep knowledge about linear algebra, algebraic structure, number theory, and other high level math knowledge to build O(min(n,k)^3) solution). Need exactly 2 weeks to prepare everything until I publish it on SPOJ.


Added by:Tjandra Satria Gunawan
Date:2013-06-23
Time limit:100s
Source limit:50000B
Memory limit:1536MB
Cluster: Cube (Intel G860)
Languages:All except: ASM64
Resource:Modified Swap (Original) problem