Compare commits
5 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| 56df7a6c40 | |||
| e05095f6bf | |||
| b1d9a282e7 | |||
| 89c6cbe9b8 | |||
|
f4174b8898
|
@@ -1,4 +1,4 @@
|
||||
iimport java.math.BigInteger;
|
||||
import java.math.BigInteger;
|
||||
import java.util.HashSet;
|
||||
import java.util.Set;
|
||||
import java.util.concurrent.TimeUnit; // Optional: for more readable time output
|
||||
@@ -8,7 +8,7 @@ import java.util.concurrent.TimeUnit; // Optional: for more readable time output
|
||||
* for 2 <= a <= 100 and 2 <= b <= 100.
|
||||
* This implementation runs on a single core/thread.
|
||||
*/
|
||||
public class DistinctPowers {
|
||||
public class Problem029 {
|
||||
|
||||
// Define the inclusive range for base 'a'
|
||||
private static final int MIN_A = 2;
|
||||
|
||||
94
java/Problem323.java
Normal file
94
java/Problem323.java
Normal file
@@ -0,0 +1,94 @@
|
||||
import java.math.BigDecimal;
|
||||
import java.math.MathContext;
|
||||
import java.math.RoundingMode;
|
||||
|
||||
/**
|
||||
* Calculates the expected number of steps N until a 32-bit integer,
|
||||
* initially zero, becomes all ones (2^32 - 1) by repeatedly performing
|
||||
* a bitwise OR with a sequence of random 32-bit integers.
|
||||
*
|
||||
* The expected value is calculated using the formula:
|
||||
* E[N] = sum_{j=0 to infinity} (1 - (1 - (1/2)^j)^M)
|
||||
* where M = 32.
|
||||
*
|
||||
* This program approximates the sum by summing a fixed number of terms
|
||||
* using high-precision BigDecimal arithmetic.
|
||||
*/
|
||||
public class Problem323 {
|
||||
|
||||
public static void main(String[] args) {
|
||||
|
||||
// --- Configuration ---
|
||||
final int M = 32; // Exponent (number of bits)
|
||||
// Number of terms in the sum (j=0 to ITERATIONS-1).
|
||||
// Chosen based on analysis to provide sufficient precision.
|
||||
final int ITERATIONS = 70;
|
||||
// Precision for BigDecimal calculations (number of significant digits)
|
||||
// Chosen to be >> 10
|
||||
final int PRECISION = 50;
|
||||
// Final scale for the result (decimal places)
|
||||
final int FINAL_SCALE = 10;
|
||||
// Rounding mode for calculations and final result
|
||||
final RoundingMode ROUNDING_MODE = RoundingMode.HALF_UP;
|
||||
|
||||
// --- Setup High Precision ---
|
||||
// MathContext defines precision and rounding rules for operations
|
||||
MathContext mc = new MathContext(PRECISION, ROUNDING_MODE);
|
||||
|
||||
// BigDecimal constants for efficiency and clarity
|
||||
final BigDecimal ZERO = BigDecimal.ZERO;
|
||||
final BigDecimal ONE = BigDecimal.ONE;
|
||||
final BigDecimal TWO = new BigDecimal("2");
|
||||
|
||||
// --- Calculation ---
|
||||
BigDecimal expectedValueSum = ZERO;
|
||||
// Initialize halfPowerJ to (1/2)^0 = 1
|
||||
BigDecimal halfPowerJ = ONE;
|
||||
|
||||
System.out.println("Calculating E[N] using " + ITERATIONS + " terms with precision " + PRECISION + "...");
|
||||
|
||||
for (int j = 0; j < ITERATIONS; j++) {
|
||||
// Calculate the term Tj = 1 - (1 - (1/2)^j)^M
|
||||
|
||||
// 1. Calculate base: (1 - (1/2)^j)
|
||||
BigDecimal termBase = ONE.subtract(halfPowerJ);
|
||||
|
||||
// 2. Calculate base^M: (1 - (1/2)^j)^M
|
||||
// Use pow(int n, MathContext mc) for controlled precision during exponentiation
|
||||
BigDecimal termBasePowM = termBase.pow(M, mc);
|
||||
|
||||
// 3. Calculate Tj = 1 - base^M
|
||||
BigDecimal termTj = ONE.subtract(termBasePowM);
|
||||
|
||||
// 4. Add Tj to the running sum
|
||||
expectedValueSum = expectedValueSum.add(termTj, mc);
|
||||
|
||||
// 5. Prepare (1/2)^j for the *next* iteration (j+1)
|
||||
// (1/2)^(j+1) = (1/2)^j / 2
|
||||
halfPowerJ = halfPowerJ.divide(TWO, mc);
|
||||
|
||||
// Optional: Print progress every 10 iterations
|
||||
// if ((j + 1) % 10 == 0) {
|
||||
// System.out.println("j=" + j + ", Current Sum=" + expectedValueSum.round(new MathContext(FINAL_SCALE + 2)));
|
||||
// }
|
||||
}
|
||||
|
||||
// System.out.println("Calculation complete.");
|
||||
|
||||
// --- Round final result ---
|
||||
BigDecimal finalResult = expectedValueSum.setScale(FINAL_SCALE, ROUNDING_MODE);
|
||||
|
||||
// --- Output ---
|
||||
System.out.println("\nCalculated Expected Value E[N]:");
|
||||
// Use toPlainString() to avoid potential scientific notation
|
||||
System.out.println(finalResult.toPlainString());
|
||||
|
||||
// --- Sanity Check (Approximate value based on theoretical analysis) ---
|
||||
double log2_M = Math.log(M) / Math.log(2.0);
|
||||
double gamma = 0.57721566490153286060; // Euler-Mascheroni constant
|
||||
double ln2 = Math.log(2.0);
|
||||
double approxExpectedValue = log2_M + gamma / ln2 + 0.5;
|
||||
System.out.println("\nApproximate theoretical value (for comparison): " + String.format("%.10f", approxExpectedValue));
|
||||
|
||||
}
|
||||
}
|
||||
94
scratch/Misc_301-400/323/ExpectedValueN.java
Normal file
94
scratch/Misc_301-400/323/ExpectedValueN.java
Normal file
@@ -0,0 +1,94 @@
|
||||
import java.math.BigDecimal;
|
||||
import java.math.MathContext;
|
||||
import java.math.RoundingMode;
|
||||
|
||||
/**
|
||||
* Calculates the expected number of steps N until a 32-bit integer,
|
||||
* initially zero, becomes all ones (2^32 - 1) by repeatedly performing
|
||||
* a bitwise OR with a sequence of random 32-bit integers.
|
||||
*
|
||||
* The expected value is calculated using the formula:
|
||||
* E[N] = sum_{j=0 to infinity} (1 - (1 - (1/2)^j)^M)
|
||||
* where M = 32.
|
||||
*
|
||||
* This program approximates the sum by summing a fixed number of terms
|
||||
* using high-precision BigDecimal arithmetic.
|
||||
*/
|
||||
public class ExpectedValueN {
|
||||
|
||||
public static void main(String[] args) {
|
||||
|
||||
// --- Configuration ---
|
||||
final int M = 32; // Exponent (number of bits)
|
||||
// Number of terms in the sum (j=0 to ITERATIONS-1).
|
||||
// Chosen based on analysis to provide sufficient precision.
|
||||
final int ITERATIONS = 70;
|
||||
// Precision for BigDecimal calculations (number of significant digits)
|
||||
// Chosen to be >> 10
|
||||
final int PRECISION = 50;
|
||||
// Final scale for the result (decimal places)
|
||||
final int FINAL_SCALE = 10;
|
||||
// Rounding mode for calculations and final result
|
||||
final RoundingMode ROUNDING_MODE = RoundingMode.HALF_UP;
|
||||
|
||||
// --- Setup High Precision ---
|
||||
// MathContext defines precision and rounding rules for operations
|
||||
MathContext mc = new MathContext(PRECISION, ROUNDING_MODE);
|
||||
|
||||
// BigDecimal constants for efficiency and clarity
|
||||
final BigDecimal ZERO = BigDecimal.ZERO;
|
||||
final BigDecimal ONE = BigDecimal.ONE;
|
||||
final BigDecimal TWO = new BigDecimal("2");
|
||||
|
||||
// --- Calculation ---
|
||||
BigDecimal expectedValueSum = ZERO;
|
||||
// Initialize halfPowerJ to (1/2)^0 = 1
|
||||
BigDecimal halfPowerJ = ONE;
|
||||
|
||||
System.out.println("Calculating E[N] using " + ITERATIONS + " terms with precision " + PRECISION + "...");
|
||||
|
||||
for (int j = 0; j < ITERATIONS; j++) {
|
||||
// Calculate the term Tj = 1 - (1 - (1/2)^j)^M
|
||||
|
||||
// 1. Calculate base: (1 - (1/2)^j)
|
||||
BigDecimal termBase = ONE.subtract(halfPowerJ);
|
||||
|
||||
// 2. Calculate base^M: (1 - (1/2)^j)^M
|
||||
// Use pow(int n, MathContext mc) for controlled precision during exponentiation
|
||||
BigDecimal termBasePowM = termBase.pow(M, mc);
|
||||
|
||||
// 3. Calculate Tj = 1 - base^M
|
||||
BigDecimal termTj = ONE.subtract(termBasePowM);
|
||||
|
||||
// 4. Add Tj to the running sum
|
||||
expectedValueSum = expectedValueSum.add(termTj, mc);
|
||||
|
||||
// 5. Prepare (1/2)^j for the *next* iteration (j+1)
|
||||
// (1/2)^(j+1) = (1/2)^j / 2
|
||||
halfPowerJ = halfPowerJ.divide(TWO, mc);
|
||||
|
||||
// Optional: Print progress every 10 iterations
|
||||
// if ((j + 1) % 10 == 0) {
|
||||
// System.out.println("j=" + j + ", Current Sum=" + expectedValueSum.round(new MathContext(FINAL_SCALE + 2)));
|
||||
// }
|
||||
}
|
||||
|
||||
// System.out.println("Calculation complete.");
|
||||
|
||||
// --- Round final result ---
|
||||
BigDecimal finalResult = expectedValueSum.setScale(FINAL_SCALE, ROUNDING_MODE);
|
||||
|
||||
// --- Output ---
|
||||
System.out.println("\nCalculated Expected Value E[N]:");
|
||||
// Use toPlainString() to avoid potential scientific notation
|
||||
System.out.println(finalResult.toPlainString());
|
||||
|
||||
// --- Sanity Check (Approximate value based on theoretical analysis) ---
|
||||
double log2_M = Math.log(M) / Math.log(2.0);
|
||||
double gamma = 0.57721566490153286060; // Euler-Mascheroni constant
|
||||
double ln2 = Math.log(2.0);
|
||||
double approxExpectedValue = log2_M + gamma / ln2 + 0.5;
|
||||
System.out.println("\nApproximate theoretical value (for comparison): " + String.format("%.10f", approxExpectedValue));
|
||||
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user