I want define a symbolic function
var('x')
f(x)=(x+1)%8
but I get the follow error
TypeError: unable to convert x (=x) to an integer
How I will be able to fix this?
We don't have symbolic modulo in that sense. Indeed,
sage: x%2
---------------------------------------------------------------------------
TypeError Traceback (most recent call last)
TypeError: unable to convert x (=x) to an integer
sage: mod(x+1,8) gives a similar error, for similar reasons.
You can make a Python function, of course.
sage: def f(x):
....: return (x+1)%8
....:
sage: f(55)
0
sage: f(56)
1
sage: f(57)
2
If we knew what you wanted to do with your function, it might be possible to find a workaround. I'm assuming you don't want to take the derivative, and that you only want integer inputs, so it's not clear that a "symbolic" version would even be appropriate.
Related
I'm starting to learn Julia, and I was wondering if there is an equivalent function in Julia that is doing the same as the epsilon function in Fortran.
In Fortran, the epsilon function of variable x gives the smallest number of the same kind of x that satisfies 1+epsilon(x)>1
I thought the the function eps() in Julia would be something similar, so I tried
eps(typeof(x))
but I got the error:
MethodError: no method matching eps(::Type{Int64})
Is there any other function that resembles the Fortran one that can be used on the different variables of the code?
If you really need eps to work for both Float and Int types, you can overload a method of eps for Int by writing Base.eps(Int) = one(Int). Then your code will work. This is okay for personal projects, but not a good idea for code you intend to share.
As the docstring for eps says:
help?> eps
eps(::Type{T}) where T<:AbstractFloat
eps()
eps is only defined for subtypes of AbstractFloat i.e. floating point numbers. It seems that your variable x is an integer variable, as the error message says no method matching eps(::Type{Int64}). It doesn't really make sense to define an eps for integers since the "the smallest number of the same kind of x that satisfies 1 + epsilon(x) > 1" is always going to be 1 for integers.
If you did want to get a 1 of the specific type of integer you have, you can use the one function instead:
julia> x = UInt8(42)
0x2a
julia> one(typeof(x))
0x01
It seems like what you actually want is
eps(x)
not
eps(typeof(x))
The former is exactly equivalent to your Fortran function.
I am trying to write a simple histogram program that takes a stream of unknown (very large) length, integers only, and bins them up. My problem doesn't relate to binning so we can assume that the integers can be in range (0, 1000] and the histogram bins are of size 1 (each possible number gets its own bin).
Normally I would do this with reduce and its variants in whatever programming language, and I write something like that in Julia (using an array in place of the actual file-based iterator i am using as input):
function ct_a(arr, i)
arr[i] += 1
end
reduce(ct_a, [100, 140, 471, 900, 999], init=zeros(1000))
Now i've tried variants such as changing the order of arguments and so on but get a variety of seeming type or signature related issues:
ERROR: MethodError: no method matching reduce(::typeof(ct_b), ::Array{Int64,1}, ::Array{Int64,1})
ERROR: MethodError: no method matching reduce(::typeof(ct_a), ::Array{Int64,1}, ::Array{Int64,1})
ERROR: MethodError: no method matching setindex!(::Int64, ::Int64, ::Int64)
This seems like it should work because AFAIK there is no formal reason why the output of a reduce operation needs to resemble the type of the individual elements being iterated over. Every example I can find online however about the use of reduce in julia supposes that the memo (output) is of like type (i.e., the op operator being passed in is of type F: T,T -> T.) This seems like an arbitrary restriction and unlikely to be the case, but i can't figure out how to do this differently.
I have been able to circumvent this issue somehow by using a function like F: T,T->null and storing the memo globally:
memo=zeros(1000)
function ct_x(_, i)
memo[i] += 1
end
reduce(ct_x, [1,2,3,100,200,900], init="whatever")
Is there an intended way to express reduce functions of this nature?
You need your reduction function to return the modified array, not the modified element value. Try this:
function ct_a(arr, i)
arr[i] += 1
arr
end
julia> reduce(ct_a, [2, 3, 4], init=zeros(Int, 5))
5-element Array{Int64,1}:
0
1
1
1
0
This is what I want to happen:
[m | m<-[1..1000], k<-[3,5], m `mod` k == 0]
When I put that code in the console I get the result I want but when I try to turn it into a generalized function Haskell is just spitting out tons of errors and I cannot figure out how to make it work.
This is what I have:
multiplesOfKLessThanN :: Num a => [a] -> a -> [a]
multiplesOfKLessThanN ks n = [m | m<-[1..n], k<-ks, m `mod` k == 0]
problem1 = putStrLn(show(multiplesOfKLessThanN([3,5] 1000)))
main = problem1
One Such Error I am getting:
Couldn't match expected type 'Integer -> [a0]' with actual type '[Integer]'
I also get other errors but inconsistently. This is something I have noticed with Haskell, it likes to change error messages even when the code hasn't changed at all like wtf?
Your use of mutliplesOfKLessThanN is not correct
mutliplesOfKLessThanN([3,5] 1000)
Is not interpreted by Haskell as
Apply mutliplesOfKLessThanN with [3,5] and 1000.
but instead it is interpteted as
Apply [3,5] to 1000 and apply multiplesOfKLessThanN to the result.
I think your misconception is in how function application occurs. In many languages function application requires parentheses e.g. f(x). For Haskell parentheses only ever mean "do this operation first", and function application is achieved by putting things next to each other. So f(x) works in Haskell because it is the same as f x, but f(x y) is the same as f(x(y)) and tells Haskell to evaluate x y first and then give it to f.
With your code Haskell can't apply [3,5] as a function, which is what Haskell is telling you, it expected a function (in fact a specific type of function).
The proper way to write this would be
multiplesOfKLessThanN [3,5] 1000
This should handle that main error you are getting.
So the error here is a type error because you are trying to make a more general type a be used by the function modulo. If you look at the type mod it expects an integral type class changing your constraint from Num to Integral should resolve your issue
I am learning Julia, Here is something I am unable to figure out.
Case1: I started Julia console and overridden the default sqrt function with a number 10. So now the function doesn't work. To me coming from R its bit of surprise, In R usually even if we override a function it works because of the method dispatch. Clearly, Julia's way of doing it is different which is okay. But now I am unable to reset to its natural state. I have to restart Julia to make it(sqrt) work again.
julia> sqrt = 10
10
julia> sqrt(5)
ERROR: MethodError: objects of type Int64 are not callable
Stacktrace:
[1] top-level scope at REPL[2]:1
julia> sqrt = Nothing
Nothing
julia> sqrt(5)
ERROR: MethodError: no method matching Nothing(::Int64)
Closest candidates are:
Nothing() at boot.jl:324
Stacktrace:
[1] top-level scope at REPL[4]:1
Case2: I started Julia console and used sqrt function to calculate things and it worked. But now if I try to reset to a constant it's not working. (I am assuming its because its compiled already and hence can't be overridden).
julia> sqrt(7)
2.6457513110645907
julia> sqrt = 10
ERROR: cannot assign a value to variable Base.sqrt from module Main
Stacktrace:
[1] top-level scope at REPL[2]:1
My question is:
Is there any way to reset the function to original state without restarting Julia?
Also is my assumption for case2 is correct?
I am not sure if its already answered somewhere. I tried to find it out, but couldn't. I am still giving a read on this thing. But asking for help if anyone knows this. Thanks in advance.
AFAIU, the rationale for this behavior is as follows:
when you run sqrt(5) in a program, it means that you know about the sqrt function. If, later on, you try to assign a new value to sqrt, Julia forbids you to do so, on the grounds that sqrt in your program actually refers to the Base.sqrt function, which is a constant. (Note that the same is true of any function that got exported by a package you're using; there is no specificity related to Base here, except that you don't have to explicitly using Base in order to be able to call the functions it defines).
if you don't use sqrt first as a function, Julia can't assume that you know about Base.sqrt. So if the first mention of sqrt in your program is an assignment, it will happily create a new variable of that name. This makes Julia more future-proof: suppose that you write a program that declares and uses a variable named foo. As of Julia 1.5.3, no Base.foo function exists. But now imagine that Julia 1.6 introduces a Base.foo function. We wouldn't want such a change to break your existing code, which should continue working with newer Julia versions. Therefore the safe choice in this case consists in letting you freely declare a variable foo without worrying about the name collision with Base.foo.
Now in the case where you accidentally create in an interactive session a global variable that collides with an existing function, a simple solution would be to simply reassign your variable to the function from Base (or whichever module the original function came from):
julia> sqrt = 1
1
# Oops, looks like I made a mistake
julia> sqrt(2)
ERROR: MethodError: objects of type Int64 are not callable
Stacktrace:
[1] top-level scope at REPL[2]:1
# Let's try and fix it
julia> sqrt = Base.sqrt
sqrt (generic function with 20 methods)
julia> sqrt(2)
1.4142135623730951
I'm using the Dates module and I'm trying to convert a Seconds object to an integer.
When I try the following, I get an error:
x = Second(5)
Int(x)
# ERROR: MethodError: no method matching Int64(::Second)
Why doesn't this work? How do I just extract this as a integer value?
My question also applies to converting minutes to integer, days to integer, months to integer, etc.
Instead of using an Int constructor, access the .value property of the Second object:
x = Second(5)
x.value # 5
This works for the other objects from the Dates module such as Minute, Day, Month, etc.
Check out #tholy's answer too for a great explanation of why it's structured like this.
As a side note, dump() is a helpful function in situations like this - when you're working with an unfamiliar object and you want to understand how to access its attributes and so forth:
dump(x)
# Output:
# Second
# value: Int64 5
To expand on the answer from J. Blauvelt, the omission of convert(Int, d) is deliberate. The reason is that convert often implies equivalence, and is used automatically when adding elements to containers:
julia> c = [1,2]
2-element Array{Int64,1}:
1
2
julia> push!(c, Second(5))
ERROR: MethodError: Cannot `convert` an object of type Second to an object of type Int64
Closest candidates are:
convert(::Type{T<:Number}, ::T<:Number) where T<:Number at number.jl:6
convert(::Type{T<:Number}, ::Number) where T<:Number at number.jl:7
convert(::Type{T<:Integer}, ::Ptr) where T<:Integer at pointer.jl:23
...
Stacktrace:
[1] push!(::Array{Int64,1}, ::Second) at ./array.jl:853
[2] top-level scope at none:0
If you allowed this kind of automatic conversion, you could get quite confused: for example, push!(c, Day(5)) would also put 5 into c, and suddenly you're in a situation where you've implied that Day(5) == Second(5).
Now, constructor syntax Int(t) is not the same as convert(Int, t). So in principle, perhaps this could be allowed. But historically the two were intertwined, and there may be a fair amount of code that doesn't distinguish the two.
Consequently, when you're asking for something related to the internal representation, for now it seems better to require the user to exploit that representation directly (e.g., t = Second(5); t.value). Or, write your code in a way that allows you to keep these values along with their units.