import java.io.*;
import java.lang.Double;
import java.lang.Long;
import java.lang.Math;
import java.lang.String;

public class rwinfnanascii
{
    public static final String Progname = "rwinfnanascii";

    public static void main(String[] args) throws IOException
    {
	double x, y, z;

	test_inf(1.0, 0.0);		// generate a positive Infinity
	test_inf(-1.0, 0.0);		// generate a negative Infinity
	test_nan(0.0, 0.0);		// generate a positive NaN
	// test_nan(Math.sqrt(-0.0), 0.0);	// generate a negative NaN
	test_nan(-0.0, 0.0);		// generate a negative NaN
    }

    public static String doubleToHexadecimal(double x)
    {
	long lx = Double.doubleToLongBits(x);
	String s = Long.toHexString(lx);

	return ("0x" + s);
    };

    public static void read_and_check(String inname) throws IOException
    {
	FileInputStream in = new FileInputStream(inname);
	StreamTokenizer tokens = new StreamTokenizer(in);

	double x, y, z, expect;

	// System.out.println("========================================================================");

	x = y = z = -999;

	// tokens.parseNumbers();
	if (tokens.nextToken() != tokens.TT_EOF)
	{
	    x = tokens.nval;
	    tokens.nextToken();
	    y = tokens.nval;
	    tokens.nextToken();
	    z = tokens.nval;
	}

	expect = x / y;

	System.out.println("Read from ASCII text file:");
	System.out.print  ("\t" + x + " [" + doubleToHexadecimal(x) + "] / ");
	System.out.print  (y + " [" + doubleToHexadecimal(y) + "] -> ");
	System.out.println(z + " [" + doubleToHexadecimal(z) + "]");
	System.out.print  ("\tExpected: " + expect + " [" + doubleToHexadecimal(expect) + "]");
	if (Double.isNaN(z))
	    System.out.println(Double.isNaN(expect) ? " [correct]" : " [INCORRECT]");
	else if (Double.isInfinite(z))
	    System.out.println(Double.isInfinite(expect) ? " [correct]" : " [INCORRECT]");
	else
	    System.out.println((!Double.isInfinite(expect) &&
				!Double.isNaN(expect) &&
				(z == expect)) ? " [correct]" : " [INCORRECT]");

	in.close();
	System.out.println("========================================================================");
    }

    public static void test_inf(double x, double y) throws IOException
    {
	String tmpname = Progname + ".tmp.inf";
	// FileOutputStream tmpfile = new FileOutputStream(tmpname);
	PrintStream tmpfile = new PrintStream(new FileOutputStream(tmpname));
	PrintWriter output = new PrintWriter(tmpfile);
	double z = x / y;

	System.out.println("This line should read: " + x + "/" + y + " -> +/-Infinity");
	System.out.println(x + "/" + y + " -> " + z);

	// output.println(x + " " + y + " " + z);
	tmpfile.print(x);
	tmpfile.print(' ');
	tmpfile.print(y);
	tmpfile.print(' ');
	tmpfile.print(z);
	tmpfile.print('\n');

	if (z != z)
	   System.out.println("INCORRECT comparison of Infinities with !=");
	if (z == z)
	   System.out.println("Correct comparison of Infinities with ==");

	if (!Double.isInfinite(z))
	   System.out.println("INCORRECT test of Infinities with isInfinite()");
	if (Double.isInfinite(z))
	   System.out.println("Correct test of Infinities with isInfinite()");

	tmpfile.close();
	read_and_check(tmpname);
    }

    public static void test_nan(double x, double y) throws IOException
    {
	String tmpname = Progname + ".tmp.nan";
	// FileOutputStream tmpfile = new FileOutputStream(tmpname);
	PrintStream tmpfile = new PrintStream(new FileOutputStream(tmpname));
	PrintWriter output = new PrintWriter(tmpfile);
	double z = x / y;

	System.out.println("This line should read: " + x + "/" + y + " -> +/-NaN");
	System.out.println(x + "/" + y + " -> " + z);

	// output.println(x + " " + y + " " + z);
	tmpfile.print(x);
	tmpfile.print(' ');
	tmpfile.print(y);
	tmpfile.print(' ');
	tmpfile.print(z);
	tmpfile.print('\n');

	if (z == z)
	   System.out.println("INCORRECT comparison of NaNs with !=");
	if (z != z)
	   System.out.println("Correct comparison of NaNs with ==");

	if (!Double.isNaN(z))
	   System.out.println("INCORRECT test of NaNs with isNaN()");
	if (Double.isNaN(z))
	   System.out.println("Correct test of NaNs with isNaN()");
	tmpfile.close();
	read_and_check(tmpname);
    }
}
