Data Unit Converter — Java source
Convert between digital data units - B, KB/KiB, MB/MiB, GB/GiB, TB/TiB. Switch between decimal (1000) and binary (1024) bases, runs entirely in your browser.
This is the Java implementation — the same logic the interactive tool runs, in a shareable, citable form.
// =============================================================================
// DataUnitConverter.java — CosmoDev polyglot showcase port of the
// `data-unit-converter` tool
// -----------------------------------------------------------------------------
// Language : Java (Java 17, standard library only)
// Source: ported from src/lib/dataUnits.ts (the canonical, live TypeScript
// lib); mirrors src/tool-sources/data-unit-converter/{python.py,rust.rs}
// License : display source — part of CosmoDev's polyglot tool pages
// (dev.cosmolabs.org). Shown verbatim alongside the JS/TS/Go/Rust/
// Python ports and the other language ports.
// -----------------------------------------------------------------------------
// Pure digital-data unit conversion. Convert between B, KB/KiB, MB/MiB,
// GB/GiB, TB/TiB: the decimal base 1000 pairs with KB/MB/GB/TB (SI) and the
// binary base 1024 with KiB/MiB/GiB/TiB (IEC). Deterministic and
// side-effect free; convertData returns Double.NaN for non-finite input,
// unknown unit symbols, or an invalid base — never throws.
// =============================================================================
package org.cosmolabs.cosmodev;
import java.util.List;
import java.util.Map;
/**
* Pure digital-data unit conversion for the Data Unit Converter tool on
* CosmoDev (dev.cosmolabs.org).
*/
public final class DataUnitConverter {
private DataUnitConverter() {
}
/**
* Units available under each base, ordered smallest (B) to largest. The
* UI uses this to populate the per-base unit pickers. Unmodifiable, like
* every collection this class exposes.
*/
private static final Map<Integer, List<String>> UNITS = Map.of(
1000, List.of("B", "KB", "MB", "GB", "TB"),
1024, List.of("B", "KiB", "MiB", "GiB", "TiB"));
/**
* Power-of-base rank for each unit symbol: "B" is rank 0 and each prefix
* step adds 1. KB and KiB are both rank 1 — the unit picks the rank, the
* base decides whether a rank means ×1000 or ×1024.
*/
private static final Map<String, Integer> EXPONENTS = Map.ofEntries(
Map.entry("B", 0),
Map.entry("KB", 1), Map.entry("MB", 2), Map.entry("GB", 3), Map.entry("TB", 4),
Map.entry("KiB", 1), Map.entry("MiB", 2), Map.entry("GiB", 3), Map.entry("TiB", 4));
/**
* Units available under {@code base} (1000 or 1024), ordered smallest to
* largest, or {@code null} for an invalid base.
*/
public static List<String> unitsFor(int base) {
return UNITS.get(base);
}
/**
* Converts a value between two digital-data units under the given base.
*
* <p>Strategy: reduce to bytes via {@code value × base^fromExp}, then
* divide by {@code base^toExp}. Returns {@code Double.NaN} for non-finite
* input (Inf/NaN), unknown unit symbols, or a base other than 1000/1024 —
* never throws (mirrors the TypeScript contract).
*
* @param value the magnitude to convert, in {@code fromUnit}
* @param fromUnit source unit symbol, e.g. "MB"
* @param toUnit target unit symbol, e.g. "GiB"
* @param base conversion radix: 1000 (decimal/SI) or 1024 (binary/IEC)
* @return the converted magnitude, or {@code Double.NaN} on invalid input
*/
public static double convertData(double value, String fromUnit, String toUnit, int base) {
// Reject Inf/NaN early so they don't propagate through the multiplication.
if (Double.isNaN(value) || Double.isInfinite(value)) {
return Double.NaN;
}
// Only the two canonical bases are valid; anything else is a caller bug.
if (base != 1000 && base != 1024) {
return Double.NaN;
}
// Unknown unit symbols miss the map (null) — treat as invalid.
Integer fromExp = EXPONENTS.get(fromUnit);
Integer toExp = EXPONENTS.get(toUnit);
if (fromExp == null || toExp == null) {
return Double.NaN;
}
return (value * Math.pow(base, fromExp)) / Math.pow(base, toExp);
}
}
Also available in 13 other languages
Every CosmoDev tool ships its pure logic in TypeScript (web) and Go (CLI), with authored implementations in a dozen-plus languages — the same contract, ported. Compare all languages side by side →