added partial sqrt function

This commit is contained in:
hyung-hwan 2018-04-03 14:02:40 +00:00
parent 67c16596a8
commit d5097b998a
4 changed files with 101 additions and 1 deletions

View File

@ -3952,6 +3952,62 @@ oops_einval:
return HCL_NULL;
}
hcl_oop_t hcl_sqrtint (hcl_t* hcl, hcl_oop_t x)
{
/* TODO: find a faster and more efficient algorithm??? */
hcl_oop_t a, b, m, m2, t;
a = hcl->_nil;
b = hcl->_nil;
m = hcl->_nil;
m2 = hcl->_nil;
hcl_pushtmp (hcl, &x);
hcl_pushtmp (hcl, &a);
hcl_pushtmp (hcl, &b);
hcl_pushtmp (hcl, &m);
hcl_pushtmp (hcl, &m2);
a = HCL_SMOOI_TO_OOP(1);
b = hcl_bitshiftint(hcl, x, HCL_SMOOI_TO_OOP(-5));
if (!b) goto oops;
b = hcl_addints(hcl, b, HCL_SMOOI_TO_OOP(8));
if (!b) goto oops;
while (1)
{
t = hcl_geints(hcl, b, a);
if (!t) return HCL_NULL;
if (t == hcl->_false) break;
m = hcl_addints(hcl, a, b);
if (!m) goto oops;
m = hcl_bitshiftint(hcl, m, HCL_SMOOI_TO_OOP(-1));
if (!m) goto oops;
m2 = hcl_mulints(hcl, m, m);
if (!m2) goto oops;
t = hcl_gtints(hcl, m2, x);
if (!t) return HCL_NULL;
if (t == hcl->_true)
{
b = hcl_subints(hcl, m, HCL_SMOOI_TO_OOP(1));
if (!b) goto oops;
}
else
{
a = hcl_addints(hcl, m, HCL_SMOOI_TO_OOP(1));
if (!a) goto oops;
}
}
hcl_poptmps (hcl, 5);
return hcl_subints(hcl, a, HCL_SMOOI_TO_OOP(1));
oops:
hcl_poptmps (hcl, 5);
return HCL_NULL;
}
hcl_oop_t hcl_inttostr (hcl_t* hcl, hcl_oop_t num, int radix, int ngc)
{
hcl_ooi_t v = 0;

View File

@ -940,6 +940,11 @@ hcl_oop_t hcl_leints (
hcl_oop_t y
);
hcl_oop_t hcl_sqrtint (
hcl_t* hcl,
hcl_oop_t x
);
hcl_oop_t hcl_strtoint (
hcl_t* hcl,
const hcl_ooch_t* str,
@ -1038,6 +1043,13 @@ hcl_oop_t hcl_nenums (
hcl_oop_t x,
hcl_oop_t y
);
hcl_oop_t hcl_sqrtnum (
hcl_t* hcl,
hcl_oop_t x
);
/* ========================================================================= */
/* comp.c */
/* ========================================================================= */

View File

@ -335,7 +335,6 @@ hcl_oop_t hcl_lenums (hcl_t* hcl, hcl_oop_t x, hcl_oop_t y)
return comp_nums(hcl, x, y, hcl_leints);
}
hcl_oop_t hcl_eqnums (hcl_t* hcl, hcl_oop_t x, hcl_oop_t y)
{
return comp_nums(hcl, x, y, hcl_eqints);
@ -344,3 +343,25 @@ hcl_oop_t hcl_nenums (hcl_t* hcl, hcl_oop_t x, hcl_oop_t y)
{
return comp_nums(hcl, x, y, hcl_neints);
}
hcl_oop_t hcl_sqrtnum (hcl_t* hcl, hcl_oop_t x)
{
if (!HCL_IS_FPDEC(hcl, x))
{
return hcl_sqrtint(hcl, x);
}
else
{
/* TODO: debug this part... this part is buggy. not complete yet */
hcl_oop_t v;
hcl_ooi_t scale;
scale = HCL_OOP_TO_SMOOI(((hcl_oop_fpdec_t)x)->scale);
v = ((hcl_oop_fpdec_t)x)->value;
v = hcl_sqrtint(hcl, v);
if (!v) return HCL_NULL;
return hcl_makefpdec(hcl, v, scale / 2);
}
}

View File

@ -499,6 +499,16 @@ static hcl_pfrc_t pf_number_rem (hcl_t* hcl, hcl_mod_t* mod, hcl_ooi_t nargs)
return HCL_PF_SUCCESS;
}
static hcl_pfrc_t pf_number_sqrt (hcl_t* hcl, hcl_mod_t* mod, hcl_ooi_t nargs)
{
hcl_oop_t ret;
ret = hcl_sqrtnum(hcl, HCL_STACK_GETARG(hcl, nargs, 0)); /*TODO: change to hcl_sqrtnum()*/
if (!ret) return HCL_PF_FAILURE;
HCL_STACK_SETRET (hcl, nargs, ret);
return HCL_PF_SUCCESS;
}
static hcl_pfrc_t pf_number_gt (hcl_t* hcl, hcl_mod_t* mod, hcl_ooi_t nargs)
{
hcl_oop_t ret;
@ -585,6 +595,7 @@ static pf_t builtin_prims[] =
{ 1, HCL_TYPE_MAX(hcl_oow_t), pf_number_div, 1, { '/' } },
{ 1, HCL_TYPE_MAX(hcl_oow_t), pf_number_quo, 3, { 'q','u','o' } },
{ 2, HCL_TYPE_MAX(hcl_oow_t), pf_number_rem, 3, { 'm','o','d' } },
{ 1, 1, pf_number_sqrt, 4, { 's','q','r','t' } },
{ 2, 2, pf_number_gt, 1, { '>' } },
{ 2, 2, pf_number_ge, 2, { '>','=' } },