Problem:
Score : 400 points

Problem Statement

We say that a odd number N is similar to 2017 when both N and (N+1)/2 are prime.

You are given Q queries.

In the i-th query, given two odd numbers l_i and r_i, find the number of odd numbers x similar to 2017 such that l_i ≤ x ≤ r_i.

Constraints

1≤Q≤10^5

1≤l_i≤r_i≤10^5

l_i and r_i are odd.

All input values are integers.

Input

Input is given from Standard Input in the following format:

Q
l_1 r_1
:
l_Q r_Q

Output

Print Q lines. The i-th line (1≤i≤Q) should contain the response to the i-th query.

Sample Input 1

1
3 7

Sample Output 1

2

3 is similar to 2017, since both 3 and (3+1)/2=2 are prime.

5 is similar to 2017, since both 5 and (5+1)/2=3 are prime.

7 is not similar to 2017, since (7+1)/2=4 is not prime, although 7 is prime.

Thus, the response to the first query should be 2.

Sample Input 2

4
13 13
7 11
7 11
2017 2017

Sample Output 2

1
0
0
1

Note that 2017 is also similar to 2017.

Sample Input 3

6
1 53
13 91
37 55
19 51
73 91
13 49

Sample Output 3

4
4
1
1
1
2

Solution in Rust (1.15.1) (judge verdict: Accepted)

#[test]
fn test_solve() {
   assert_eq!(solve("1\n3 7\n"), "2\n");
   assert_eq!(solve("4\n13 13\n7 11\n7 11\n2017 2017\n"), "1\n0\n0\n1\n");
   assert_eq!(solve("6\n1 53\n13 91\n37 55\n19 51\n73 91\n13 49\n"), "4\n4\n1\n1\n1\n2\n");
}
fn solve(src: &str) -> String {
    let mut sc = Scanner::from_str(src);

    const MAX:usize = 50_000;

    let ipm = is_prime_table(2*MAX);
    let mut sum = vec![0; MAX+1];
    for i in 0..MAX {
        sum[i+1] = sum[i];
        if ipm[2*i+1] && ipm[i+1] {
            sum[i+1] += 1;
        } 
    }
    
    let mut ret = String::new();
    use std::fmt::Write;
    
    let q: usize = sc.read();
    for _ in 0..q {
        let l: usize = sc.read();
        let r: usize = sc.read();
        let (l, r) = (l >> 1, r >> 1);
        writeln!(&mut ret, "{}", sum[r+1] - sum[l]).unwrap();
    }
    
    ret
}
fn is_prime_table(n: usize) -> Vec<bool> {
    let mut ipm = vec![true; n + 1];
    ipm[0] = false;
    ipm[1] = false;
    let nsr = (n as f64).sqrt() as usize;
    for p in 2..nsr + 1 {
        if ipm[p] {
            let mut mpp = 2 * p;
            while mpp <= n {
                ipm[mpp] = false;
                mpp += p;
            }
        }
    }
    ipm
}
fn main() {
    let mut buf = String::new();
    use std::io::{Read, Write};
    std::io::stdin().read_to_string(&mut buf).unwrap();
    std::io::stdout().write_all(solve(&buf).as_bytes()).unwrap();
}
struct Scanner<'a>(std::str::SplitWhitespace<'a>);
impl<'a> Scanner<'a> {
    fn from_str(src: &str) -> Scanner {
        Scanner(src.split_whitespace())
    }
    fn get(&mut self) -> &str {
        self.0.next().unwrap()
    }
    fn read<T: std::str::FromStr>(&mut self) -> T {
        self.get().parse().ok().unwrap()
    }
}