Cod sursa(job #3289015)

Utilizator lucky1992Ion Ion lucky1992 Data 25 martie 2025 10:52:24
Problema Principiul includerii si excluderii Scor 100
Compilator java Status done
Runda Arhiva educationala Marime 3.16 kb
import java.io.*;
import java.util.ArrayList;
import java.util.List;
import java.util.StringTokenizer;

public class Main {

  public static List<Long> primes;

  public static class MyScanner implements Closeable {
    BufferedReader br;
    StringTokenizer st;

    public MyScanner(String file) throws FileNotFoundException {
      br = new BufferedReader(new InputStreamReader(new FileInputStream(file)), 1 << 16);
    }

    String next() {
      while (st == null || !st.hasMoreElements()) {
        try {
          st = new StringTokenizer(br.readLine());
        } catch (IOException e) {
          e.printStackTrace();
        }
      }
      return st.nextToken();
    }

    int nextInt() {
      return Integer.parseInt(next());
    }

    long nextLong() {
      return Long.parseLong(next());
    }

    double nextDouble() {
      return Double.parseDouble(next());
    }

    String nextLine(){
      String str = "";
      try {
        str = br.readLine();
      } catch (IOException e) {
        e.printStackTrace();
      }
      return str;
    }

    @Override
    public void close() throws IOException {
      br.close();
    }
  }

  public static List<Long> divisors(long v) {
    List<Long> divs = new ArrayList<>();

    long d = 2;

    while (v > 1 && d * d <= v) {
      if (v  % d == 0) {
        divs.add(d);

        do {
          v = v / d;
        } while (v % d == 0);
      }

      if (d == 2) {
        d++;
      } else {
        d += 2;
      }
    }

    if (v > 1) {
      divs.add(v);
    }

    return divs;
  }

  public static List<Long> divisorsWithPrimes(long v) {
    List<Long> divs = new ArrayList<>();

//    long d = 2;

    int k = 0;

    while (v > 1 && primes.get(k) * primes.get(k) <= v) {
      long d = primes.get(k);
      if (v  % d == 0) {
        divs.add(d);

        do {
          v = v / d;
        } while (v % d == 0);
      }

      k++;
    }

    if (v > 1) {
      divs.add(v);
    }

    return divs;
  }

  public static long compute(long A, long B) {
    List<Long> divisors = divisorsWithPrimes(B);

    long count = 0;

    for (int i = 1; i < (1 << divisors.size()); i++) {
      long prod = 1;
      int nr = 0;
      for (int j = 0; j < divisors.size(); j++) {
        if (((1 << j) & i) != 0) {
          nr++;
          prod *= divisors.get(j);
        }
      }

      if (nr % 2 == 1) {
        count += (A / prod);
      } else {
        count -= (A / prod);
      }
    }

    return count;
  }

  public static List<Long> sieve(int N) {
    boolean[] sieve = new boolean[N+1];
    List<Long> primes = new ArrayList<>();

    for (int i = 2; i <= N; i++) {
      if (!sieve[i]) {
        primes.add((long)i);
        for (int j = i + i; j <= N; j += i) {
          sieve[j] = true;
        }
      }
    }

    return primes;
  }



  public static void main(String[] args) throws IOException {
    try(MyScanner scanner = new MyScanner("pinex.in");
        PrintWriter pw = new PrintWriter("pinex.out")) {
      int M = scanner.nextInt();
      primes = sieve(1_000_000);
      for (int i = 1; i <= M; i++) {
        long A = scanner.nextLong();
        long B = scanner.nextLong();
        pw.println(A - compute(A, B));
      }
    }
  }
}