unit MathD;
{$MODE objfpc}
{$INLINE ON}
(***************************************)
(* Copyright (C) 2017, SHIRAISHI Kazuo *)
(***************************************)
interface

uses
  Classes, SysUtils,
  arithmet;

function InitNumber(sig1:extended;exp1:smallint):Number;
{$IFDEF FPC_HAS_TYPE_EXTENDED}
Operator := (x : extended) n : number;
Operator := (n : number) x : extended;
{$ENDIF}
Operator := (n : number) x : double;
//Operator := (n : number) x : LongInt;
Operator := (x : double) n : number;
Operator - (n : number) x : number;
Operator + (x,y : number) z : number;
Operator - (x,y : number) z : number;
Operator * (x,y : number) z : number;
Operator / (x,y : number) z : number;
operator = (x, y : number) b : boolean;
operator < (x, y : number) b : boolean;
operator <= (x, y : number) b : boolean;
operator > (x, y : number) b : boolean;
operator >= (x, y : number) b : boolean;
function dadd (x,y : number): number;
function dsbt (x,y : number) : number;
function dmlt (x,y : number) : number;
function ddiv (x,y : number) : number;
function dpower  (x,y : number) : number;
function dsquare (x: number) : number;
function opposite  (x: number) : number;

function sign( x:Number):Number;  overload;
function SGN( x:Number):Number;   overload;
function ABS(x: number) : number; overload;
function BCEIL(x: number) : number; overload;
function EPS(x: number) : number;  overload;
FUNCTION BINT(x: number) : number; overload;
function BMOD(x,y : number) : number; overload;
function IP(x: number) : number;  overload;
function FP(x: number) : number;  overload;
function REMAINDER(x,y:number):number;overload;
function TRUNCATE( x,y:number):number;overload;
function ROUND( x:number):number;     overload;
function ROUND( x,y:number):number;   overload;
function BMIN(x,y : number) : number; overload;
function BMAX(x,y : number) : number; overload;
function ValidDecimal(x:Number;extyp:integer):Number;
{TNumber}
type
   TNumber = class
      value:Number;
     constructor create(n:Number);
     function str:ansistring;
   end;

function NumericVariable(var x:Number; a:Number):PNumber;  overload;


implementation
 uses
   base2;

function InitNumber(sig1:extended;exp1:smallint):Number;
begin
  with result do
    begin
      sig:=sig1;
      exp:=exp1;
    end;
   normalize1(result);
  checkRangeDecimal(result,1001);
end;
{$IFDEF FPC_HAS_TYPE_EXTENDED}
Operator := (n : number) x : extended;
begin
  x:=extendedval(n);
end;
Operator := (x : extended) n : number;
begin
  InitDecimal(n,x);
  //RoundVariable(n);
end;
{$ENDIF}
Operator := (n : number) x : double;
begin
  x:=extendedval(n);
end;
{
Operator := (n : number) x : LongInt;
begin
   x:=LongIntRound(extendedval(n));
end;
}
Operator := (x : double) n : number;
begin
  InitDecimal(n,x);
  //RoundVariable(n);
end;

function dadd (x,y : number): number;
begin
  add(x,y,result)
end;

function dsbt (x,y : number) : number;
begin
  sbt(x,y,result)
end;

function dmlt (x,y : number) : number;
begin
  mlt(x,y,result)
end;

function ddiv (x,y : number) : number;
begin
  qtt(x,y,result)
end;

Operator + (x,y : number) z : number;
begin
  add(x,y,z)
end;

Operator - (x,y : number) z : number;
begin
  sbt(x,y,z)
end;

Operator * (x,y : number) z : number;
begin
  mlt(x,y,z)
end;

Operator / (x,y : number) z : number;
begin
  qtt(x,y,z)
end;

operator = (x, y : number) b : boolean;
begin
  b:=(arithmet.compare(x,y)=0)
end;

operator < (x, y : number) b : boolean;
begin
  b:=(arithmet.compare(x,y)<0)
end;

operator <= (x, y : number) b : boolean;
begin
  b:=(arithmet.compare(x,y)<=0)
end;

operator > (x, y : number) b : boolean;
begin
  b:=(arithmet.compare(x,y)>0)
end;

operator >= (x, y : number) b : boolean;
begin
  b:=(arithmet.compare(x,y)>=0)
end;

function dpower  (x,y : number) : number;
begin
  arithmet.power(x,y,result)
end;

function dsquare (x: number) : number;
begin
   arithmet.square(x);
   result:=x;
end;

function opposite  (x: number) : number;
begin
   arithmet.opposite(x);
   result:=x;
end;

Operator - (n : number) x : number;
begin
   arithmet.opposite(n);
   x:=n;
end;


function ABS(x: number) : number;
begin
    arithmet.absolute(x);
    result:=x
end;
function BCEIL(x: number) : number;
begin
    arithmet.ceil(x);
    result:=x
end;
function EPS(x: number) : number;
begin
    arithmet.EpsDecimal(x);
    result:=x
end;

function FP(x: number) : number;
begin
    arithmet.FractPart(x);
    result:=x
end;

FUNCTION BINT(x: number) : number;
begin
    arithmet.BASICINT(x);
    result:=x
end;

function IP(x: number) : number;
begin
    Arithmet.intpart(x);
    result:=x
end;

function BMOD(x,y : number) : number;
begin
    arithmet.BasicMOD(x,y,result)
end;

function REMAINDER(x,y : number) : number;
begin
    arithmet.remainder(x,y,result)
end;

function TRUNCATE(x,y:Number):Number; overload;
 begin
    Arithmet.truncate(x,y,result)
 end;

function BMIN(x,y : number) : number;
begin
    arithmet.min(x,y,result)
end;

function BMAX(x,y : number) : number;
begin
    arithmet.max(x,y,result)
end;

function SGN( x:Number):Number;
begin
    initInteger(result,arithmet.sgn(@x));
end;

function sign( x:Number):Number;
begin
    initInteger(result,arithmet.sgn(@x));
end;

function ROUND( x:number):number;
begin
 arithmet.IntRound(x);
 result:=x;
end;

function ROUND( x,y:number):number;
begin
  arithmet.round(x,y,result)
end;

constructor TNumber.create(n:Number);
begin
   inherited create;
   value:=n;
end;

function TNumber.str:ansistring;
begin
  result:=DSTR(value)
end;

function NumericVariable(var x:Number; a:Number):PNumber; inline;
begin
   x:=a;
   result:=@x
end;

function ValidDecimal(x:Number;extyp:integer):Number;
begin
  arithmet.checkRangeDecimal(x,extyp);
  result:=x;
end;

initialization

end.

