"It's a base 2 fractional number with no exact decimal expansion with a finite number of digits. Display it in base 2 fractional form if you don't want to see an approximation."
Binary numbers are a countably infinite set. Decimal numbers are a countably infinite set. You can therefore map binary representation to decimal representation 1-1 with a simple mapping function.
OTOH, floating point numbers are an uncountably infinite set. The only way to map binary numbers to floating point numbers is to map to a strict subset.
The subset happens to be different when mapping binary to floating point and decimal to floating point when using IEEE754.
Anyway, mathematicians don't use numbers at all - debasing the equations by performing caculations with them is so.. gauche. Leave that to the physicists, chemists and engineers.
Well, which data type would you like to store the value of PI in? I mean, you could re-calculate it to arbitrary precision every time you use it... just don't try to store it at "full" precision using floats or decimals.
If it where me I'd store the value of PI as a structure containing an IEEE double, a decimal representation of, say, 100 digits and a pointer to a function to that can evaluate PI to an arbitrary precision.
Then I'd just just use PI as a symbol and do symbolic algebra for as long as possible. Don't evaluate it to anything until the user actually asks for a numeric representation. Once a numeric representation is required I'd pick a value from the above structure based on what has been asked for.
the CS: "Hey, it's round off error. Get used to it"
the Mathematician: "Fix IT!!"