Skip to content

Commit

Permalink
Merge pull request #26 from GiggleLiu/polish-lognumber
Browse files Browse the repository at this point in the history
update log number operations
  • Loading branch information
GiggleLiu authored Aug 8, 2020
2 parents 2b5b80f + 5004389 commit 66e4e05
Show file tree
Hide file tree
Showing 7 changed files with 55 additions and 23 deletions.
4 changes: 2 additions & 2 deletions Project.toml
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
name = "NiLang"
uuid = "ab4ef3a6-0b42-11ea-31f6-e34652774712"
authors = ["JinGuo Liu", "thautwarm"]
version = "0.7.1"
version = "0.7.2"

[deps]
FixedPointNumbers = "53c48c17-4a7d-5ca2-90c5-79b7896eea93"
Expand All @@ -14,7 +14,7 @@ SparseArrays = "2f01184e-e22b-5df5-ae63-d93ebab69eaf"
TupleTools = "9d95972d-f1c8-5527-a6e0-b4b365fa01f6"

[compat]
FixedPointNumbers = "0.6"
FixedPointNumbers = "0.6, 0.7, 0.8"
LogarithmicNumbers = "0.4"
MatchCore = "0.1"
NiLangCore = "0.7"
Expand Down
31 changes: 17 additions & 14 deletions examples/fixedlog.jl
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
using FixedPointNumbers, Test

"""
## Reference
[1] C. S. Turner, "A Fast Binary Logarithm Algorithm", IEEE Signal
Expand All @@ -8,29 +10,30 @@ function log2fix(x::Fixed{T, P}) where {T, P}
x.i == 0 && return typemin(T) # represents negative infinity

y = zero(T)
xi = unsigned(x.i)
while xi < UInt(1) << PREC
xi <<= UInt(1)
y -= 1 << PREC
xi = x.i
while xi < 1 << PREC
xi <<= 1
y -= T(1) << PREC
end

while xi >= UInt(2) << PREC
xi >>= UInt(1)
y += 1 << PREC
while xi >= 2 << PREC
xi >>= 1
y += T(1) << PREC
end

z = Int128(xi)
b = 1 << (PREC - UInt(1))
z = xi
b = T(1) << (PREC - UInt(1))
for i = 1:P
z = (z * z) >> PREC
if z >= 2 << PREC
z >>= UInt(1)
temp = Base.widemul(z, z) >> PREC
z = T(temp)
if z >= T(2) << PREC
z >>= 1
y += b
end
b >>= UInt(1)
b >>= 1
end

return Fixed{T,PREC}(y, nothing)
end

@test log2fix(Fixed43(2^1.24)) 1.24
@test log2fix(Fixed{Int, 43}(2^1.24)) 1.24
1 change: 0 additions & 1 deletion src/autodiff/vars.jl
Original file line number Diff line number Diff line change
Expand Up @@ -160,7 +160,6 @@ end
_content(x::ULogarithmic) = x.log
for T in [:ULogarithmic]
@eval NiLang.AD.GVar(x::$T) = default_constructor($T, GVar(_content(x), zero(_content(x))))
@eval (_::Type{Inv{$T}})(x::$T) = _content(x)
#@eval NiLang.AD.grad(x::$T{<:GVar}) = default_constructor($T, grad(_content(x)))
@eval (_::Type{Inv{GVar}})(x::$T{<:GVar}) = default_constructor($T, (~GVar)(_content(x)))

Expand Down
18 changes: 13 additions & 5 deletions src/ulog.jl
Original file line number Diff line number Diff line change
Expand Up @@ -6,31 +6,39 @@ function NiLangCore.default_constructor(ln::Type{<:ULogarithmic}, x)
exp(ULogarithmic, x)
end

@i @inline function (:*=(identity))(x::T, y::T) where T<:ULogarithmic
@i @inline function (:*=(identity))(x::ULogarithmic, y::ULogarithmic)
x.log += y.log
end

@i @inline function (:*=(identity))(x::ULogarithmic, y::Real)
x.log += log(y)
end

for (OP1, OP2, OP3) in [(:*, :+, :(+=)), (:/, :-, :(-=))]
@eval @i @inline function (:*=($OP1))(out!::T, x::T, y::T) where T<:ULogarithmic
@eval @i @inline function (:*=($OP1))(out!::ULogarithmic, x::ULogarithmic, y::ULogarithmic)
out!.log += $OP2(x.log, y.log)
end

@eval @i @inline function (:*=($OP1))(out!::T, x::Real, y::Real) where T<:ULogarithmic
@eval @i @inline function (:*=($OP1))(out!::ULogarithmic, x::Real, y::Real)
out!.log += log(x)
$(Expr(OP3, :(out!.log), :(log(y))))
end

@eval @i @inline function (:*=($OP1))(out!::T, x::T, y::Real) where T<:ULogarithmic
@eval @i @inline function (:*=($OP1))(out!::ULogarithmic, x::ULogarithmic, y::Real)
out!.log += x.log
$(Expr(OP3, :(out!.log), :(log(y))))
end

@eval @i @inline function (:*=($OP1))(out!::T, x::Real, y::T) where T<:ULogarithmic
@eval @i @inline function (:*=($OP1))(out!::ULogarithmic, x::Real, y::ULogarithmic)
out!.log += log(x)
$(Expr(OP3, :(out!.log), :(y.log)))
end
end

@i @inline function (:*=(^))(out!::ULogarithmic, x::ULogarithmic, y::Real)
out!.log += x.log * y
end

gaussian_log(x) = log1p(exp(x))
gaussian_nlog(x) = log1p(-exp(x))

Expand Down
6 changes: 5 additions & 1 deletion src/vars.jl
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
# variable manipulation
export @zeros
export @zeros, @ones

"""
Create zeros of specific type.
Expand All @@ -15,6 +15,10 @@ macro zeros(T, args...)
esc(Expr(:block, map(x->:($x zero($T)), args)...))
end

macro ones(T, args...)
esc(Expr(:block, map(x->:($x one($T)), args)...))
end

function NiLangCore.chfield(a::AbstractArray, ::typeof(vec), val)
reshape(val, size(a)...)
end
12 changes: 12 additions & 0 deletions test/ulog.jl
Original file line number Diff line number Diff line change
Expand Up @@ -23,4 +23,16 @@ using NiLangCore: default_constructor
default_constructor(ULogarithmic, 3.0)
@instr x *= y - z
@test x.log log(exp(7.0) * (exp(5.0) - exp(3.0)))

x, y, z = default_constructor(ULogarithmic, 7.0),
default_constructor(ULogarithmic, 5.0),
default_constructor(ULogarithmic, 3.0)
@instr x *= y^3.4
@test x.log log(exp(5.0)^3.4 * exp(7.0))

x, y, z = default_constructor(ULogarithmic, 7.0),
default_constructor(ULogarithmic, 5.0),
default_constructor(ULogarithmic, 3.0)
@instr x *= 3
@test x.log log(exp(7.0) * 3)
end
6 changes: 6 additions & 0 deletions test/vars.jl
Original file line number Diff line number Diff line change
Expand Up @@ -6,4 +6,10 @@ using Test, NiLang
b zero(Float64)
c zero(Float64)
end)

@test (@macroexpand @ones Float64 a b c) == :(begin
a one(Float64)
b one(Float64)
c one(Float64)
end)
end

0 comments on commit 66e4e05

Please sign in to comment.