This commit is contained in:
blueloveTH 2023-09-22 20:08:34 +08:00
parent c939ad727b
commit 71234ae73c
5 changed files with 19 additions and 10 deletions

View File

@ -101,11 +101,12 @@ union BitsCvtImpl<4>{
NumberTraits<4>::float_t _float; NumberTraits<4>::float_t _float;
// 1 + 8 + 23 // 1 + 8 + 23
unsigned int sign() const noexcept { return _int >> 31; } int sign() const noexcept { return _int >> 31; }
unsigned int exp() const noexcept { return (_int >> 23) & 0b1111'1111; } unsigned int exp() const noexcept { return (_int >> 23) & 0b1111'1111; }
uint64_t mantissa() const noexcept { return _int & 0x7fffff; } uint64_t mantissa() const noexcept { return _int & 0x7fffff; }
void set_exp(uint64_t exp) noexcept { _int = (_int & 0x807f'ffff) | (exp << 23); } void set_exp(int exp) noexcept { _int = (_int & 0x807f'ffff) | (exp << 23); }
void set_sign(int sign) noexcept { _int = (_int & 0x7fff'ffff) | (sign << 31); }
void zero_mantissa() noexcept { _int &= 0xff80'0000; } void zero_mantissa() noexcept { _int &= 0xff80'0000; }
static constexpr int C0 = 127; // 2^7 - 1 static constexpr int C0 = 127; // 2^7 - 1
@ -130,11 +131,12 @@ union BitsCvtImpl<8>{
NumberTraits<8>::float_t _float; NumberTraits<8>::float_t _float;
// 1 + 11 + 52 // 1 + 11 + 52
unsigned int sign() const noexcept { return _int >> 63; } int sign() const noexcept { return _int >> 63; }
unsigned int exp() const noexcept { return (_int >> 52) & 0b0111'1111'1111; } unsigned int exp() const noexcept { return (_int >> 52) & 0b0111'1111'1111; }
uint64_t mantissa() const noexcept { return _int & 0xfffffffffffff; } uint64_t mantissa() const noexcept { return _int & 0xfffffffffffff; }
void set_exp(uint64_t exp) noexcept { _int = (_int & 0x800f'ffff'ffff'ffff) | (exp << 52); } void set_exp(uint64_t exp) noexcept { _int = (_int & 0x800f'ffff'ffff'ffff) | (exp << 52); }
void set_sign(uint64_t sign) noexcept { _int = (_int & 0x7fff'ffff'ffff'ffff) | (sign << 63); }
void zero_mantissa() noexcept { _int &= 0xfff0'0000'0000'0000; } void zero_mantissa() noexcept { _int &= 0xfff0'0000'0000'0000; }
static constexpr int C0 = 1023; // 2^10 - 1 static constexpr int C0 = 1023; // 2^10 - 1
@ -195,9 +197,8 @@ inline PyObject* tag_float(f64 val){
BitsCvt decomposed(val); BitsCvt decomposed(val);
// std::cout << "tagging: " << val << std::endl; // std::cout << "tagging: " << val << std::endl;
// decomposed.print(); // decomposed.print();
// std::cout << "exp: " << decomposed.exp() << std::endl; int sign = decomposed.sign();
int exp_7b = decomposed.exp() - BitsCvt::C0; int exp_7b = decomposed.exp() - BitsCvt::C0;
// std::cout << "exp_7b: " << exp_7b << std::endl;
if(exp_7b < BitsCvt::C1){ if(exp_7b < BitsCvt::C1){
exp_7b = BitsCvt::C1 - 1; // -63 + 63 = 0 exp_7b = BitsCvt::C1 - 1; // -63 + 63 = 0
decomposed.zero_mantissa(); decomposed.zero_mantissa();
@ -208,6 +209,7 @@ inline PyObject* tag_float(f64 val){
decomposed.set_exp(exp_7b + BitsCvt::C2); decomposed.set_exp(exp_7b + BitsCvt::C2);
// decomposed.print(); // decomposed.print();
decomposed._int = (decomposed._int << 1) | 0b01; decomposed._int = (decomposed._int << 1) | 0b01;
decomposed.set_sign(sign);
// decomposed.print(); // decomposed.print();
return reinterpret_cast<PyObject*>(decomposed._int); return reinterpret_cast<PyObject*>(decomposed._int);
} }

View File

@ -383,11 +383,9 @@ void init_builtins(VM* _vm) {
auto py_number_pow = [](VM* vm, PyObject* lhs_, PyObject* rhs_) { auto py_number_pow = [](VM* vm, PyObject* lhs_, PyObject* rhs_) {
i64 lhs, rhs; i64 lhs, rhs;
if(try_cast_int(lhs_, &lhs) && try_cast_int(rhs_, &rhs)){ if(try_cast_int(lhs_, &lhs) && try_cast_int(rhs_, &rhs)){
bool flag = false;
if(rhs < 0) { if(rhs < 0) {
if(lhs == 0) vm->ZeroDivisionError("0.0 cannot be raised to a negative power"); if(lhs == 0) vm->ZeroDivisionError("0.0 cannot be raised to a negative power");
flag = true; return VAR((f64)std::pow(lhs, rhs));
rhs = -rhs;
} }
i64 ret = 1; i64 ret = 1;
while(rhs){ while(rhs){
@ -395,7 +393,6 @@ void init_builtins(VM* _vm) {
lhs *= lhs; lhs *= lhs;
rhs >>= 1; rhs >>= 1;
} }
if(flag) return VAR((f64)(1.0 / ret));
return VAR(ret); return VAR(ret);
}else{ }else{
return VAR((f64)std::pow(CAST_F(lhs_), CAST_F(rhs_))); return VAR((f64)std::pow(CAST_F(lhs_), CAST_F(rhs_)));

View File

@ -1,7 +1,7 @@
# test int literals # test int literals
assert 0xffff == 65535 assert 0xffff == 65535
assert 0xAAFFFF == 11206655 assert 0xAAFFFF == 11206655
assert 0x7fffffff == 2147483647 # will fail on 32-bit systems assert 0x7fffffff == 2147483647
# test == != >= <= < > # test == != >= <= < >
assert -1 == -1 assert -1 == -1

View File

@ -45,3 +45,13 @@ assert eq(float(1.5), 1.5)
assert eq(float(-1.5), -1.5) assert eq(float(-1.5), -1.5)
assert eq(float("123"), 123.0) assert eq(float("123"), 123.0)
assert eq(float("123.456"), 123.456) assert eq(float("123.456"), 123.456)
import math
inf = float("inf")
assert 1/0 == inf
assert -1/0 == -inf
assert 1/inf == 0
assert -1/inf == 0
assert math.isnan(0/0)