hecfda’s C++ core ports all 13 distribution families from HEC.FDA.Statistics. Every family is addressed the same way: a name string and a numeric parameter vector, in the order the core factory expects (the same order the fixtures/distributions/*.json oracle files use). One generic set of functions covers all of them: dist_pdf(), dist_cdf(), dist_quantile(), and dist_sample().
Nine families are reachable this way, through the generic factory dispatch:
Family
Name string
Parameter order
Notes
Normal
"Normal"
mean, sd, sample_size
Uniform
"Uniform"
min, max, sample_size
Triangular
"Triangular"
min, most_likely, max, sample_size
Deterministic
"Deterministic"
value
a point mass
LogNormal
"LogNormal"
mean, sd, sample_size
moments of the natural-log-scale data
TruncatedNormal
"TruncatedNormal"
mean, sd, min, max, sample_size
TruncatedLogNormal
"TruncatedLogNormal"
mean, sd, min, max, sample_size
moments of the natural-log-scale data
LogPearsonIII
"LogPearsonIII"
mean, sd, skew, sample_size
moments of the log10-scale data; the flood-frequency workhorse
TruncatedLogPearson3
"TruncatedLogPearson3"
mean, sd, skew, min, max, sample_size
moments of the log10-scale data
Four of the 13 families are not on this list, and calling dist_pdf() with any of their names raises an error rather than constructing one. Gamma, ShiftedGamma, and PearsonIII are internal helper classes in the C++ core, not members of the IDistribution factory, so they have no name string at all. Empirical is a full IDistribution member, but is not constructible by name through the factory: it is built from data (a histogram or a set of quantiles), not from a short parameter vector, so it has its own construction path rather than a dist_pdf()-style entry point. See the porting status page for where each of these lives.
Density, CDF, and quantile
Two families illustrate the range hecfda covers: Normal, a light-tailed, symmetric distribution, and LogPearsonIII, the heavy-tailed flood-frequency distribution HEC-FDA uses for annual peak flows. Both plots below evaluate dist_pdf(), dist_cdf(), and dist_quantile() over a grid and draw the three curves in the same earth-tone palette used throughout these examples.
x =seq(-4, 4, length.out =200)p =seq(0.001, 0.999, length.out =200)params =c(0, 1, 1)par(mfrow =c(1, 3))plot(x, dist_pdf("Normal", params, x), type ="l", col ="#6b705c", lwd =2,xlab ="x", ylab ="density", main ="pdf")plot(x, dist_cdf("Normal", params, x), type ="l", col ="#a5a58d", lwd =2,xlab ="x", ylab ="probability", main ="cdf")plot(p, dist_quantile("Normal", params, p), type ="l", col ="#cb997e", lwd =2,xlab ="probability", ylab ="x", main ="quantile")
Normal(mean = 0, sd = 1)
x =seq(100, 12000, length.out =200)p =seq(0.01, 0.99, length.out =200)params =c(3.3, 0.254, 0.0925, 99)par(mfrow =c(1, 3))plot(x, dist_pdf("LogPearsonIII", params, x), type ="l", col ="#6b705c", lwd =2,xlab ="x", ylab ="density", main ="pdf")plot(x, dist_cdf("LogPearsonIII", params, x), type ="l", col ="#a5a58d", lwd =2,xlab ="x", ylab ="probability", main ="cdf")plot(p, dist_quantile("LogPearsonIII", params, p), type ="l", col ="#cb997e", lwd =2,xlab ="probability", ylab ="x", main ="quantile")
dist_sample() draws n values by applying the seeded generator’s uniform stream through inverse_cdf(), the same path every Monte Carlo compute in hecfda uses. A histogram of 1000 seeded Normal draws should track the analytic density closely:
draws =dist_sample("Normal", c(0, 1, 1), n =1000L, seed =12345L)hist(draws, breaks =30, freq =FALSE, col ="#a5a58d", border ="white",xlab ="x", main ="")x =seq(-4, 4, length.out =200)lines(x, dist_pdf("Normal", c(0, 1, 1), x), col ="#588157", lwd =2)
1000 seeded draws from Normal(0, 1) against the analytic pdf
fda.dist_sample("Normal", [0, 1, 1], n=1000, seed=12345) in Python draws the identical 1000 values, in the identical order, because both languages call the same seeded C++ generator.
Faithful bugs
Warning
This port reproduces upstream HEC-FDA behavior exactly, including a few known quirks in the C# source. Two examples that affect distributions:
Empirical’s pdf returns 0 for any x that is not an exact grid point in its data, rather than interpolating between points.
LogNormal mixes natural-log (ln) and log10 semantics inconsistently between its methods, matching the same inconsistency in the C# source rather than normalizing it.
These are not bugs in the port; they are the upstream behavior, transcribed on purpose so results match HEC-FDA exactly. The porting status page describes what is ported and what was left out.