163 lines
4.1 KiB
C
Executable File
163 lines
4.1 KiB
C
Executable File
#include <math.h>
|
|
#include <stdio.h>
|
|
#include <stdlib.h>
|
|
#include <string.h>
|
|
|
|
// briskei ola ta i
|
|
|
|
typedef __int128 int128_t;
|
|
|
|
int128_t power(int128_t b, int128_t ex)
|
|
{
|
|
int128_t res = (int128_t)1;
|
|
while (ex > 0) {
|
|
// If the exponent is odd, multiply the result by the current base value
|
|
if (ex % 2 == 1) { // Same as (exponent & 1)
|
|
res = (int128_t)res * b;
|
|
}
|
|
|
|
// Square the base for the next iteration
|
|
b = (int128_t)b * b;
|
|
// Halve the exponent (integer division)
|
|
ex /= (int128_t)2; // Same as (exponent >>= 1)
|
|
}
|
|
return res;
|
|
}
|
|
|
|
void print_int128(__int128 n)
|
|
{
|
|
if (n == 0) {
|
|
putchar('0');
|
|
return;
|
|
}
|
|
if (n < 0) {
|
|
putchar('-');
|
|
n = -n;
|
|
}
|
|
|
|
// A buffer to hold the digits (max digits ~40)
|
|
char buf[40];
|
|
int i = 0;
|
|
|
|
// Extract digits in reverse order
|
|
while (n > 0) {
|
|
buf[i++] = (char)((n % 10) + '0');
|
|
n /= 10;
|
|
}
|
|
|
|
// Print the digits in the correct order
|
|
while (i > 0) {
|
|
putchar(buf[--i]);
|
|
}
|
|
}
|
|
|
|
const int primes[] = {2, 3, 5};
|
|
int exponents[] = {0, 0, 0};
|
|
const int NUM_PRIMES = 3;
|
|
|
|
// Global variable to store the number N (calculated in main)
|
|
int128_t N_value = 1;
|
|
int128_t a = 1;
|
|
int128_t b = 1;
|
|
// --- Function to Recursively Generate Factor Pairs ---
|
|
|
|
/**
|
|
* @brief Recursively generates the first factor (n1) and prints the pair (n1, n2)
|
|
* such that n1 * n2 = N. The generation stops when n1 exceeds sqrt(N).
|
|
*
|
|
* @param prime_index The index of the current prime factor being considered.
|
|
* @param n1 The factor built so far.
|
|
*/
|
|
void generate_factor_pairs(int prime_index, int128_t n1, int f)
|
|
{
|
|
// Base Case: If we have considered all unique prime factors,
|
|
// n1 is a complete factor of N.
|
|
if (prime_index == NUM_PRIMES) {
|
|
// Optimization: Stop if n1 exceeds the square root of N.
|
|
// This prevents printing the pair (n2, n1) after (n1, n2) has been printed.
|
|
// Note: For large N, we should compare n1 * n1 > N_value to avoid
|
|
// issues with long long or the sqrt() function if it's less precise.
|
|
int128_t n2 = (int128_t)N_value / (int128_t)n1;
|
|
if ((int128_t)n1 > (int128_t)n2) {
|
|
return;
|
|
}
|
|
if (((int128_t)n1 + (int128_t)n2) % 2 == 0) {
|
|
int128_t i = (int128_t)a + (int128_t)b + (((int128_t)n1 + (int128_t)n2) >> 1);
|
|
int128_t k = (((int128_t)n2 - (int128_t)n1) >> 1);
|
|
if (f) {
|
|
printf("i: ");
|
|
print_int128(i);
|
|
printf(" k: ");
|
|
print_int128(k);
|
|
printf(" (");
|
|
print_int128(n1);
|
|
printf(" , ");
|
|
print_int128(n2);
|
|
printf(")");
|
|
printf("\n");
|
|
}
|
|
else {
|
|
print_int128(i);
|
|
printf("\n");
|
|
}
|
|
|
|
if ((int128_t)a + (int128_t)b - (((int128_t)n1 + (int128_t)n2) >> 1) >= 0) {
|
|
int128_t i = (int128_t)a + (int128_t)b - (((int128_t)n1 + (int128_t)n2) >> 1);
|
|
if (f) {
|
|
printf("i: ");
|
|
print_int128(i);
|
|
printf(" k: ");
|
|
print_int128(k);
|
|
printf(" (");
|
|
print_int128(n1);
|
|
printf(" , ");
|
|
print_int128(n2);
|
|
printf(")");
|
|
printf("\n");
|
|
}
|
|
else {
|
|
print_int128(i);
|
|
printf("\n");
|
|
}
|
|
}
|
|
}
|
|
return;
|
|
}
|
|
|
|
// Get the current prime and its exponent
|
|
int prime = primes[prime_index];
|
|
int exponent = exponents[prime_index];
|
|
int128_t power_of_prime = 1;
|
|
|
|
// Recursive Step: Iterate through all possible powers of the current prime
|
|
for (int i = 0; i <= exponent; i++) {
|
|
// The new factor n1 is the old n1 multiplied by (prime^i)
|
|
int128_t next_n1 = (int128_t)n1 * (int128_t)power_of_prime;
|
|
|
|
// Recursive call for the next prime factor
|
|
generate_factor_pairs(prime_index + 1, next_n1, f);
|
|
|
|
// Calculate the next power of the current prime: prime^(i+1)
|
|
if (i < exponent) {
|
|
power_of_prime *= (int128_t)prime;
|
|
}
|
|
}
|
|
}
|
|
|
|
int main(int argc, char **argv)
|
|
{
|
|
// long long triple[] = {}
|
|
int p;
|
|
sscanf(argv[1], "%d", &p);
|
|
int f;
|
|
sscanf(argv[2], "%d", &f);
|
|
a = (int128_t)power(10, p);
|
|
b = (int128_t)power(6, p);
|
|
N_value = (int128_t)4 * a * b;
|
|
exponents[0] = 2 * p + 2;
|
|
exponents[1] = p;
|
|
exponents[2] = p;
|
|
generate_factor_pairs(0, 1, 0);
|
|
}
|
|
|