Seven Lines of Julia (examples sought)

(@v1.7) pkg> add MathTeXEngine@0.4
 ├─restricted by compatibility requirements with MathTeXEngine [0a4f8689] to versions: 0.4.1-0.4.2       
 │ └─MathTeXEngine [0a4f8689] log:
 │   ├─possible versions are: 0.1.0-0.4.1 or uninstalled
 │   └─restricted to versions 0.4 by an explicit requirement, leaving only versions 0.4.0-0.4.1
 └─restricted by compatibility requirements with StructArrays [09ab397b] to versions: 0.1.0-0.3.10 or uninstalled — no versions left
   └─StructArrays [09ab397b] log:
     ├─possible versions are: 0.0.1-0.6.8 or uninstalled
     ├─restricted to versions * by an explicit requirement, leaving only versions 0.0.1-0.6.8
     ├─restricted by compatibility requirements with PooledArrays [2dfb63ee] to versions: [0.0.1-0.2.2, 0.4.2-0.6.8] or uninstalled, leaving only versions: [0.0.1-0.2.2, 0.4.2-0.6.8]     │ └─PooledArrays [2dfb63ee] log:
     │   ├─possible versions are: 0.3.0-1.4.2 or uninstalled
     │   ├─restricted to versions 1.2.1-1 by InMemoryDatasets [5c01b14b], leaving only versions 1.2.1-1.4.2
     │   │ └─InMemoryDatasets [5c01b14b] log:     │   │   ├─possible versions are: 0.7.3 or uninstalled
     │   │   └─InMemoryDatasets [5c01b14b] is fixed to version 0.7.3
     │   └─restricted to versions 1.3.0-1 by DataFrames [a93c6f00], leaving only versions 1.3.0-1.4.2    
     │     └─DataFrames [a93c6f00] log:     │       ├─possible versions are: 1.4.0 or uninstalled
     │       └─DataFrames [a93c6f00] is fixed to version 1.4.0
     └─restricted by compatibility requirements with IndexedTables [6deec6e2] to versions: 0.4.1-0.4.4, leaving only versions: 0.4.2-0.4.4
       └─IndexedTables [6deec6e2] log:
         ├─possible versions are: 0.7.4-1.0.0 or uninstalled
         ├─restricted to versions * by an explicit requirement, leaving only versions 0.7.4-1.0.0        
         ├─restricted by compatibility requirements with Compat [34da2185] to versions: 0.8.0-1.0.0 or uninstalled, leaving only versions: 0.8.0-1.0.0         │ └─Compat [34da2185] log:
         │   ├─possible versions are: 1.0.0-4.1.0 or uninstalled
         │   └─restricted to versions 3.17.0-3 by InMemoryDatasets [5c01b14b], leaving only versions 3.17.0-3.45.0
         │     └─InMemoryDatasets [5c01b14b] log: see above         └─restricted by compatibility requirements with PooledArrays [2dfb63ee] to versions: 1.0.0 or uninstalled, leaving only versions: 1.0.0
           └─PooledArrays [2dfb63ee] log: see above

seems there is a lot of “people” who disagree.

I think that’s IndexedTables holding back StructArrays. Either get rid of the former, or use a fresh environment.

This is cool, but the straight line segments seem not to be animated in steps right? I immediately jumped to the source to see what you’re doing because animating beziers with linear speed along the curve was a wish of mine once. Like a train along a track.

Yes, it’s cheating with straight-line and samples. :slight_smile: I’m not good at maths, but if I was, I’d certainly use pomax’s web page to do this sort of thing, because I like cool things like that.

1 Like

Maybe if I have time I could try and transfer some of that into a PR

2 Likes

GOTO10-like oneliner

println.(1:10 .|>_->prod(j->rand(["╱╲"...]),1:10));

prints this random pattern

╲╱╲╱╲╲╲╲╱╱
╱╱╲╲╱╲╱╲╲╲
╲╱╱╱╱╲╱╲╲╱
╱╲╲╲╲╲╲╲╱╲
╱╱╲╲╱╱╱╱╱╲
╲╲╱╲╲╱╲╲╲╱
╲╱╱╲╲╱╱╲╱╲
╱╲╱╱╱╱╲╲╲╲
╱╱╲╱╲╱╱╱╲╲
╱╲╱╱╱╱╲╲╱╱

change the “palette” for more generative fun. For example, ╒╓╔╕╖╗╘╙╚╛╜╝╞╟ yields

╗╟╒╘╟╝╗╒╛╔
╞╘╝╝╓╘╗╖╙╒
╓╟╘╘╒╙╚╒╛╘
╒╖╒╙╗╝╒╔╛╘
╓╘╘╛╜╝╙╔╞╞
╜╛╞╖╔╓╟╛╛╚
╞╞╗╖╒╘╕╕╒╗
╔╞╖╞╚╗╝╔╗╗
╔╚╛╝╔╚╞╙╘╟
╙╚╝╚╒╓╔╕╞╛
17 Likes

A propos: code golf - Maze generating one liner - Code Golf Stack Exchange

3 Likes

I know this is more than seven lines, but like above in the spirit of the thread.
(It’s seven lines if you ignore the setup and cleanup :stuck_out_tongue:)

using Term, REPL, UnicodePlots

begin
    t, N, Fn = REPL.TerminalMenus.terminal, 0, "15sinc(√(x^2 + y^2) / π)"
    REPL.Terminals.raw!(t, true), print(stdout, "\x1b[?25l")
    io = IOContext(PipeBuffer(), :color=>true)
    while true
        println(io, Panel(string(surfaceplot(-8:8., -8:8., eval(Meta.parse("(x, y) ->"*Fn));
            azimuth = mod(N, 360) - 180, zoom = 1.25, colormap = :jet, lines=true);
            color = true); fit = false, padding= (0, 0, 2, 2), title = Fn, width = 90, 
            justify = :center, subtitle = "[j]/[l] to rotate, [q] to quit", subtitle_justify=:right))
        REPL.Terminals.clear(t); println(read(io, String))
        c = read(stdin, Char);
        c == 'q' && break; c == 'j' && (N += 10); c == 'l' && (N -= 10)
    end
    REPL.Terminals.raw!(t, false), print(stdout, "\x1b[?25h")
end

This yields (the picture loses a little, it is interactive!)

Code partially taken from: [ANN] UnicodePlots.jl v2.8.0 - 3D plots

24 Likes

Perhaps these two variants better capture the spirit of the “until convergence” request.
Obviously there are many types of “convergences”.
Here are just two examples with somewhat naive norms.

v=[1,1,2,3,5]
F(x)=[mean(x),prod(x)^(1/length(x)), median(x)]


f(x)=partition(iterated(F,x),2)
collect(takewhile(x->!isapprox(x...), f(F(v))))[end][1]

f(x)=partition(iterated(F,x),2)
collect(last.(takewhile(Base.splat(!isapprox), f(F(v)))))


f(x)=iterated(F,x)
collect(takewhile(x->var(x)>eps(), f(v)))

Beautiful: instructive, concise, has xkcd’s “Geothmetic Meandian”.

Minor point: this calls functions not in Base. I added

using Statistics: mean, median, var

using IterTools: iterated, partition, takewhile

to the version I ran.

1 Like

using Plots; gr()
sier = scatter(1,xlim = (0, 1),ylim = (0, sqrt(3)/2), legend = false, marker = 1)
m=0.5 .* ((0,0).+ (1,0))
@gif for i=1:5000
        global m=0.5 .*(m .+ rand([(0,0),(1,0),0.5.*(1,sqrt(3))]))
        push!(sier, m)
     end every 10

sierpinski10fr25kpts

The algorithm comes from a math letters post.
The explanation, in my opinion, (not a real formal demonstration, but very substantially) lies in the fact that the operation of taking the midpoint between a generic point and one of the vertices ensures that there will never be any points in the “median triangle” (i.e. the triangle that has vertices at the midpoints of the sides) and this happens at every “level”

20 Likes

Hello! I don’t understand the syntax of wrap(x,y) operator. Can you please show me some documentation/ simple examples?

From: Control Flow · The Julia Language

The so-called “ternary operator”, ?:, is closely related to the if-elseif-else syntax, but is used where a conditional choice between single expression values is required, as opposed to conditional execution of longer blocks of code. It gets its name from being the only operator in most languages taking three operands:

a ? b : c

The expression a, before the ?, is a condition expression, and the ternary operation evaluates the expression b, before the :, if the condition a is true or the expression c, after the :, if it is false. Note that the spaces around ? and : are mandatory: an expression like a?b:c is not a valid ternary expression (but a newline is acceptable after both the ? and the :).

1 Like

An animated version of Gonway’s “Game of Life”, squeezed tightly into 7 lines.


using IterTools, Colors, FileIO

function gen(m)
    M=copy(m)
    foreach(c -> let
        snb=count(w->w==RGB(1.0,1.0,1.0),m[intersect(c .+ CartesianIndices((-1:1,-1:1)),CartesianIndices(m))]) - (m[c]==RGB(1.0,1.0,1.0))
        (m[c]==RGB(1.0,1.0,1.0) && (snb<2 || snb>3)) ? M[c]=zero(RGB) : (m[c]==zero(RGB) && snb==3) ? M[c]=RGB(1.0,1.0,1.0)  : nothing 
    end , CartesianIndices(m))
    M
end

save("init61_4x4_fps2.gif", reduce((x,y)-> [x;;;y],takestrict(iterated(gen, begin I0=zeros(RGB,9,9); I0[3:7, 5].=RGB(1.0,1.0,1.0);repeat(I0,4,4) end),30)); fps=2)

init61_4x4_fps2
game of live nX2

20 Likes
using Pkg
List = [b.name for (a, b) in reduce(vcat, [x.pkgs for x in Pkg.Registry.reachable_registries()])]
filter!(x -> !occursin("jll", x), List)
Pkg.add(rand(List))

Adds a random package.

5 Likes

You can do the filtering within the comprehension:

List = [b.name for (a, b) in reduce(vcat, [x.pkgs for x in Pkg.Registry.reachable_registries()]) if !occursin("jll", b.name)];

And the innermost square brackets can be replaced by parentheses, possibly reducing the allocations (haven’t benchmarked it, so I could be wrong).

Great thread and the examples are so creative.

I am always full of appreciation for the optimization packages in Julia.
I mostly use JuMP.jl, Convex.jl and Optim.jl but there are many and the quality is probably the highest of all similar languages (MATLAB, Python, R).

Simple example, calculating the minimum volume sphere which encloses a set of points:

using Convex;
using ECOS;

numSamples = 100;
dataDim    = 2; #<! May changed to higher dimension
mX         = randn(dataDim, numSamples); #<! Matrix of samples, each column as a sample

vC         = Variable(dataDim); #<! Center
circRadius = Variable(1); #<! Radius
sConvProb  = minimize( circRadius, [Convex.norm(vX - vC) <= circRadius for vX in eachcol(mX)] );

solve!(sConvProb, ECOS.Optimizer; silent = true);

Plotting of the scattered data (For the 2D case):

12 Likes

Here’s a slightly unusual example: it assumes you are running a Pluto notebook and have Typst installed.

With the following seven lines of Julia,

struct TypstSource
	src::String
end
function Base.show(io::IO, ::MIME"text/html", typ::TypstSource)
	cmd = pipeline(`typst compile --format svg - -`, stdin=IOBuffer(typ.src))
	write(io, read(cmd))
end

you can write Typst in your Pluto notebooks, just like markdown:

The finishing touch might be a string macro

macro typ_str(body)
	TypstSource("""
	#set page(width: 18cm, height: auto, margin: 5pt, fill: none)
	#set text(size: 13pt)
	$body
	""")
end

which puts Typst on equal footing with Markdown:

md"""
A markdown cell.
"""

typ"""
A Typst cell.
"""

Edit. You don’t even need to have typst is installed on your system; we can also use the binary wrapper. This preserves the total reproducibility of your Pluto notebook!

using Typst_jll
function Base.show(io::IO, ::MIME"image/svg+xml", typ::TypstSource)
	cmd = pipeline(`$(Typst_jll.typst()) compile --format svg - -`, stdin=IOBuffer(typ.src))
	write(io, read(cmd))
end

(Ok, this isn’t really showing off Julia itself, but it is a demonstration of how easy it is to extend the display methods and integrate with Pluto. Would this require seven lines to achieve for Jupyter notebooks?)

27 Likes

Change that to

	cmd = pipeline(`$(Typst_jll.typst()) compile --format svg - -`, stdin=IOBuffer(typ.src))
	write(io, read(cmd))

which is (a) shorter and (b) safer: JLL packages · BinaryBuilder.jl

10 Likes