Hi Everyone. I have some simple questions.
1 - What is the best(time and space wise) way to read 3 integers in a single line from stdin or a file? How about if there are arbitrary numbers of integers in a line and you need to process each(e.g. check each integer for primality)? These are inside a loop of course.
2 - Is there a faster way than printf for output?
3 - What’s the most efficient way to implement mulmod(modular multiplication) considering that the product might overflow? Is there a chance that it can be added as a built-in function like powermod(why not powmod?) and invmod?
4 - How can I have a guarantee that my local constant variable won’t be accidentally modified? From what I know, const works only for global variables.
Are you talking about parsing integers or reading them represented as binary data?
2 - Is there a faster way than printf for output?
Doing print(io, n)
is efficient.
3 - What’s the most efficient way to implement mulmod(modular multiplication) considering that the product might overflow? Is there a chance that it can be added as a built-in function like powermod(why not powmod?) and invmod?
Not really a Julia question. If you find a good algorithm for this, implementing it should be straightforward and would make either a good package or contribution to Base. I agree that the naming of invmod
and powermod
are annoyingly inconsistent. That one slipped through the 1.0 naming review process. We could always rename it to powmod
and keep powermod
as a legacy alias.
4 - How can I have a guarantee that my local constant variable won’t be accidentally modified? From what I know, const works only for global variables.
You can’t. It’s a planned feature but currently const
only works on globals.
Are you talking about parsing integers or reading them represented as binary data?
As Integers
Not really a Julia question. If you find a good algorithm for this, implementing it should be straightforward and would make either a good package or contribution to Base. I agree that the naming of
invmod
andpowermod
are annoyingly inconsistent. That one slipped through the 1.0 naming review process. We could always rename it topowmod
and keeppowermod
as a legacy alias
When will ‘powmod’ be available? ‘powermod’ is a little bit awkward to use.
Additional questions:
- Is there a plan to add ‘and’ and ‘or’ as aliases for ‘&&’ and ‘||’. These are pretty common for high level languages.
- How can I translate the below c++ code to Julia. I thought of zip but maybe there’s a better way.
for (int i = 0, j = 0, k = 0; i < 10 && j < 100 && k <1000; ++i, ++j, ++k)
You can have it whenever you like.
const powmod = powermod
No. https://github.com/JuliaLang/julia/issues/5238#issuecomment-354499909
In the general case you should consider C++ for
as equivalent to a while
construction in Julia. In some common cases it can be transformed to a Julia for
loop but that depends on how the loop variables are used. Since the loop in this case is unnecessarily complicated unless the loop variables are modified in the body, the most direct translation would be
i = j = k = 0
while i < 10 && j < 100 && k <1000
[body]
i += 1; j += 1; k += 1
end
What about using zip, like
for (i, j, k) in zip(1:10, 91:100, 991:1000)
(I had a typo in the c++ version, but the point is clear).
I don’t know how efficient “zip” is so I’m a little bit not decided on using it in this case.
And can you please add an ndigits method for a^b. Doing something like
ndigits(big(11111111111111)^1111111111111)
doesn’t work well since it seems to evaluate the expression first. So how about something like ndigits(a, b;base, pad).
Julia always evaluates what it can as soon as it can. Additionally, your expression overflows what BigInt supports. So do not expect an ndigits
version in Base Julia that will handle your example. Here is a way to get that information.
julia> using ArbNumerics, Readables
julia> ArbFloat("11111111111111")^ArbFloat("1111111111111")
3.296153757708430665985192510100e+14495286100621
julia> BigInt(ceil(log10(ans)))
14495286100622
julia> readable(ans)
14,495,286,100,622
as a macro:
using ArbNumerics
macro ndigitspow(base, power)
:(BigInt(ceil(log10(ArbFloat(string($base))^ArbFloat(string($power))))))
end
# use it like this
julia> @ndigitspow(11111111111111,1111111111111)
14495286100622
julia> a = big"11111111111111"
11111111111111
julia> b = big"1111111111111"
1111111111111
julia> @ndigitspow(a,b)
14495286100622
julia> @ndigitspow(a,a)
144952861006229
Just benchmark it and see, but it depends on what you’re doing in the body of the loop whether zip
incurs any overhead that matters. E.g. with a fairly simple body:
julia> using BenchmarkTools
julia> function f(x)
s = 0
for (i, j, k) in zip(1:10, 91:100, 991:1000)
s += x[i] + x[j] + x[k]
end
return s
end
f (generic function with 1 method)
julia> function g(x)
s = 0
i, j, k = 1, 91, 991
while i <= 10
s += x[i] + x[j] + x[k]
i += 1
j += 1
k += 1
end
return s
end
g (generic function with 1 method)
julia> x = rand(1000);
julia> @btime f($x)
22.452 ns (0 allocations: 0 bytes)
14.075682753063184
julia> @btime g($x)
8.369 ns (0 allocations: 0 bytes)
14.075682753063184