epd.c

来自「主要进行大规模的电路综合」· C语言 代码 · 共 1,315 行 · 第 1/3 页

C
1,315
字号
/**CFile***********************************************************************  FileName    [epd.c]  PackageName [epd]  Synopsis    [Arithmetic functions with extended double precision.]  Description []  SeeAlso     []  Author      [In-Ho Moon]  Copyright [ This file was created at the University of Colorado at  Boulder.  The University of Colorado at Boulder makes no warranty  about the suitability of this software for any purpose.  It is  presented on an AS IS basis.]  Revision    [$Id: epd.c,v 1.1.1.1 2003/02/24 22:23:57 wjiang Exp $]******************************************************************************/#include <stdio.h>#include <stdlib.h>#include <string.h>#include <math.h>#include "util.h"#include "epd.h"/**Function********************************************************************  Synopsis    [Allocates an EpDouble struct.]  Description [Allocates an EpDouble struct.]  SideEffects []  SeeAlso     []******************************************************************************/EpDouble *EpdAlloc(){  EpDouble	*epd;  epd = ALLOC(EpDouble, 1);  return(epd);}/**Function********************************************************************  Synopsis    [Compares two EpDouble struct.]  Description [Compares two EpDouble struct.]  SideEffects []  SeeAlso     []******************************************************************************/intEpdCmp(const char *key1, const char *key2){  EpDouble *epd1 = (EpDouble *) key1;  EpDouble *epd2 = (EpDouble *) key2;  if (epd1->type.value != epd2->type.value ||      epd1->exponent != epd2->exponent) {    return(1);  }  return(0);}/**Function********************************************************************  Synopsis    [Frees an EpDouble struct.]  Description [Frees an EpDouble struct.]  SideEffects []  SeeAlso     []******************************************************************************/voidEpdFree(EpDouble *epd){  FREE(epd);}/**Function********************************************************************  Synopsis    [Multiplies two arbitrary precision double values.]  Description [Multiplies two arbitrary precision double values.]  SideEffects []  SeeAlso     []******************************************************************************/voidEpdGetString(EpDouble *epd, char *str){  double	value;  int		exponent;  char		*pos;  if (IsNanDouble(epd->type.value)) {    sprintf(str, "NaN");    return;  } else if (IsInfDouble(epd->type.value)) {    if (epd->type.bits.sign == 1)      sprintf(str, "-Inf");    else      sprintf(str, "Inf");    return;  }  assert(epd->type.bits.exponent == EPD_MAX_BIN ||	 epd->type.bits.exponent == 0);  EpdGetValueAndDecimalExponent(epd, &value, &exponent);  sprintf(str, "%e", value);  pos = strstr(str, "e");  if (exponent >= 0) {    if (exponent < 10)      sprintf(pos + 1, "+0%d", exponent);    else      sprintf(pos + 1, "+%d", exponent);  } else {    exponent *= -1;    if (exponent < 10)      sprintf(pos + 1, "-0%d", exponent);    else      sprintf(pos + 1, "-%d", exponent);  }}/**Function********************************************************************  Synopsis    [Converts double to EpDouble struct.]  Description [Converts double to EpDouble struct.]  SideEffects []  SeeAlso     []******************************************************************************/voidEpdConvert(double value, EpDouble *epd){  epd->type.value = value;  epd->exponent = 0;  EpdNormalize(epd);}/**Function********************************************************************  Synopsis    [Multiplies two arbitrary precision double values.]  Description [Multiplies two arbitrary precision double values.]  SideEffects []  SeeAlso     []******************************************************************************/voidEpdMultiply(EpDouble *epd1, double value){  EpDouble	epd2;  double	tmp;  int		exponent;  if (EpdIsNan(epd1) || IsNanDouble(value)) {    EpdMakeNan(epd1);    return;  } else if (EpdIsInf(epd1) || IsInfDouble(value)) {    int	sign;    EpdConvert(value, &epd2);    sign = epd1->type.bits.sign ^ epd2.type.bits.sign;    EpdMakeInf(epd1, sign);    return;  }  assert(epd1->type.bits.exponent == EPD_MAX_BIN);  EpdConvert(value, &epd2);  tmp = epd1->type.value * epd2.type.value;  exponent = epd1->exponent + epd2.exponent;  epd1->type.value = tmp;  epd1->exponent = exponent;  EpdNormalize(epd1);}/**Function********************************************************************  Synopsis    [Multiplies two arbitrary precision double values.]  Description [Multiplies two arbitrary precision double values.]  SideEffects []  SeeAlso     []******************************************************************************/voidEpdMultiply2(EpDouble *epd1, EpDouble *epd2){  double	value;  int		exponent;  if (EpdIsNan(epd1) || EpdIsNan(epd2)) {    EpdMakeNan(epd1);    return;  } else if (EpdIsInf(epd1) || EpdIsInf(epd2)) {    int	sign;    sign = epd1->type.bits.sign ^ epd2->type.bits.sign;    EpdMakeInf(epd1, sign);    return;  }  assert(epd1->type.bits.exponent == EPD_MAX_BIN);  assert(epd2->type.bits.exponent == EPD_MAX_BIN);  value = epd1->type.value * epd2->type.value;  exponent = epd1->exponent + epd2->exponent;  epd1->type.value = value;  epd1->exponent = exponent;  EpdNormalize(epd1);}/**Function********************************************************************  Synopsis    [Multiplies two arbitrary precision double values.]  Description [Multiplies two arbitrary precision double values.]  SideEffects []  SeeAlso     []******************************************************************************/voidEpdMultiply2Decimal(EpDouble *epd1, EpDouble *epd2){  double	value;  int		exponent;  if (EpdIsNan(epd1) || EpdIsNan(epd2)) {    EpdMakeNan(epd1);    return;  } else if (EpdIsInf(epd1) || EpdIsInf(epd2)) {    int	sign;    sign = epd1->type.bits.sign ^ epd2->type.bits.sign;    EpdMakeInf(epd1, sign);    return;  }  value = epd1->type.value * epd2->type.value;  exponent = epd1->exponent + epd2->exponent;  epd1->type.value = value;  epd1->exponent = exponent;  EpdNormalizeDecimal(epd1);}/**Function********************************************************************  Synopsis    [Multiplies two arbitrary precision double values.]  Description [Multiplies two arbitrary precision double values.]  SideEffects []  SeeAlso     []******************************************************************************/voidEpdMultiply3(EpDouble *epd1, EpDouble *epd2, EpDouble *epd3){  if (EpdIsNan(epd1) || EpdIsNan(epd2)) {    EpdMakeNan(epd1);    return;  } else if (EpdIsInf(epd1) || EpdIsInf(epd2)) {    int	sign;    sign = epd1->type.bits.sign ^ epd2->type.bits.sign;    EpdMakeInf(epd3, sign);    return;  }  assert(epd1->type.bits.exponent == EPD_MAX_BIN);  assert(epd2->type.bits.exponent == EPD_MAX_BIN);  epd3->type.value = epd1->type.value * epd2->type.value;  epd3->exponent = epd1->exponent + epd2->exponent;  EpdNormalize(epd3);}/**Function********************************************************************  Synopsis    [Multiplies two arbitrary precision double values.]  Description [Multiplies two arbitrary precision double values.]  SideEffects []  SeeAlso     []******************************************************************************/voidEpdMultiply3Decimal(EpDouble *epd1, EpDouble *epd2, EpDouble *epd3){  if (EpdIsNan(epd1) || EpdIsNan(epd2)) {    EpdMakeNan(epd1);    return;  } else if (EpdIsInf(epd1) || EpdIsInf(epd2)) {    int	sign;    sign = epd1->type.bits.sign ^ epd2->type.bits.sign;    EpdMakeInf(epd3, sign);    return;  }  epd3->type.value = epd1->type.value * epd2->type.value;  epd3->exponent = epd1->exponent + epd2->exponent;  EpdNormalizeDecimal(epd3);}/**Function********************************************************************  Synopsis    [Divides two arbitrary precision double values.]  Description [Divides two arbitrary precision double values.]  SideEffects []  SeeAlso     []******************************************************************************/voidEpdDivide(EpDouble *epd1, double value){  EpDouble	epd2;  double	tmp;  int		exponent;  if (EpdIsNan(epd1) || IsNanDouble(value)) {    EpdMakeNan(epd1);    return;  } else if (EpdIsInf(epd1) || IsInfDouble(value)) {    int	sign;    EpdConvert(value, &epd2);    if (EpdIsInf(epd1) && IsInfDouble(value)) {      EpdMakeNan(epd1);    } else if (EpdIsInf(epd1)) {      sign = epd1->type.bits.sign ^ epd2.type.bits.sign;      EpdMakeInf(epd1, sign);    } else {      sign = epd1->type.bits.sign ^ epd2.type.bits.sign;      EpdMakeZero(epd1, sign);    }    return;  }  if (value == 0.0) {    EpdMakeNan(epd1);    return;  }  assert(epd1->type.bits.exponent == EPD_MAX_BIN);  EpdConvert(value, &epd2);  tmp = epd1->type.value / epd2.type.value;  exponent = epd1->exponent - epd2.exponent;  epd1->type.value = tmp;  epd1->exponent = exponent;  EpdNormalize(epd1);}/**Function********************************************************************  Synopsis    [Divides two arbitrary precision double values.]  Description [Divides two arbitrary precision double values.]  SideEffects []  SeeAlso     []******************************************************************************/voidEpdDivide2(EpDouble *epd1, EpDouble *epd2){  double	value;  int		exponent;  if (EpdIsNan(epd1) || EpdIsNan(epd2)) {    EpdMakeNan(epd1);    return;  } else if (EpdIsInf(epd1) || EpdIsInf(epd2)) {    int	sign;    if (EpdIsInf(epd1) && EpdIsInf(epd2)) {      EpdMakeNan(epd1);    } else if (EpdIsInf(epd1)) {      sign = epd1->type.bits.sign ^ epd2->type.bits.sign;      EpdMakeInf(epd1, sign);    } else {      sign = epd1->type.bits.sign ^ epd2->type.bits.sign;      EpdMakeZero(epd1, sign);    }    return;  }  if (epd2->type.value == 0.0) {    EpdMakeNan(epd1);    return;  }  assert(epd1->type.bits.exponent == EPD_MAX_BIN);

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?