Problem:
Score : 300 points

Problem Statement

You are given four integers A, B, C, and D. Find the number of integers between A and B (inclusive) that can be evenly divided by neither C nor D.

Constraints

1\leq A\leq B\leq 10^{18}

1\leq C,D\leq 10^9

All values in input are integers.

Input

Input is given from Standard Input in the following format:

A B C D

Output

Print the number of integers between A and B (inclusive) that can be evenly divided by neither C nor D.

Sample Input 1

4 9 2 3

Sample Output 1

2

5 and 7 satisfy the condition.

Sample Input 2

10 40 6 8

Sample Output 2

23

Sample Input 3

314159265358979323 846264338327950288 419716939 937510582

Sample Output 3

532105071133627368

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

#[allow(unused_macros)]
macro_rules! parse_line {
    ( $t:ty ) => (
        {
            let mut line = String::new();
            ::std::io::stdin().read_line(&mut line).unwrap();
            let mut iter = line.split_whitespace();
            iter.next().unwrap().parse::<$t>().unwrap()
        }
    );

    ( $( $t:ty), +) => (
        {
            let mut line = String::new();
            ::std::io::stdin().read_line(&mut line).unwrap();
            let mut iter = line.split_whitespace();
            ( $(iter.next().unwrap().parse::<$t>().unwrap()),* )
        }
    );
}

#[allow(unused_macros)]
macro_rules! read_line {
    () => {{
        let mut line = String::new();
        ::std::io::stdin().read_line(&mut line).unwrap();
        line.pop();
        line
    }};
}

#[allow(unused_macros)]
macro_rules! parse_vec {
    ( $t:ty ) => {{
        let mut line = String::new();
        ::std::io::stdin().read_line(&mut line).unwrap();
        let iter = line.split_whitespace();
        iter.map(|v| v.parse::<$t>().unwrap()).collect::<Vec<_>>()
    }};
}

fn gcd(a: u64, b: u64) -> u64 {
    if b == 0 {
        a
    } else {
        gcd(b, a % b)
    }
}

fn lcm(a: u64, b: u64) -> u64 {
    a / gcd(a, b) * b
}

fn remain(x: u64, y: u64) -> u64 {
    x - (x / y)
}

fn solve(a: u64, b: u64, c: u64, d: u64) -> u64 {
    remain(b, c) + remain(b, d)
        - remain(b, lcm(c, d))
        - (remain(a - 1, c) + remain(a - 1, d) - remain(a - 1, lcm(c, d)))
}

fn main() {
    let (a, b, c, d) = parse_line!(u64, u64, u64, u64);
    println!("{}", solve(a, b, c, d));
}

#[test]
fn remain_test() {
    assert_eq!(remain(10, 5), 8);
    assert_eq!(remain(11, 5), 9);
    assert_eq!(remain(10, 2), 5);
}

#[test]
fn solve_test() {
    assert_eq!(solve(4, 9, 2, 3), 2);
    assert_eq!(solve(1, 10, 2, 3), 3);
    assert_eq!(solve(10, 40, 6, 8), 23);
    assert_eq!(
        solve(314159265358979323, 846264338327950288, 419716939, 937510582),
        532105071133627368
    );
}