Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Mutations do not rerun cells #564

Open
DhruvaSambrani opened this issue Oct 10, 2020 · 8 comments
Open

Mutations do not rerun cells #564

DhruvaSambrani opened this issue Oct 10, 2020 · 8 comments
Labels
enhancement New feature or request reactivity The Pluto programming paradigm

Comments

@DhruvaSambrani
Copy link
Contributor

Title self explanatory

I can see why mutations don't re-run cells presently. However, is it possible to signal mutations in Julia? Makie.jl uses Observable or something, but I think(but not sure, more of a gut feel) that that has performance issues.

Further should mutations re-run cells? Does it go against the Pluto model somehow?

@dralletje
Copy link
Collaborator

As far as I know, there is no easy way to track or get notified by mutations, so it can't be on by default. Would also cause a problem as push!(x, 1) would invalidate itself and then get stuck in a loop.

Im now leaning towards something similar to observablehq mutable, as a macro that prevents the variable inside from being a dependency of the cell, and automatically invalidates the variable after the statement is executed.

Mutations don't fit the pluto-cell-reactive as nicely as immutability is, but it is something I'd rather implement as good as we can than excluding everyone who doesn't have the luxury of making copies of their matrices :P

You got any ideas? Something I'm overlooking?

@lungben
Copy link
Contributor

lungben commented Oct 14, 2020

See #316
Unfortunately, we have not found a good solution there.

@fonsp fonsp added the reactivity The Pluto programming paradigm label Oct 14, 2020
@fonsp
Copy link
Owner

fonsp commented Oct 14, 2020

I really don't know what I'm talking about but maybe we can use Cassette to inject tracking code into setfield and similar.

@fonsp
Copy link
Owner

fonsp commented Oct 15, 2020

Also I'll say that I have doubts about this feature, because it encourages 'ambiguous' notebooks, and requires complicated reactivity rules to address them. For example:

x = [1]

last(x)

push!(x, 2)

push!(x, 3)

What is the result of the second cell?

This is already a problem today (because this notebook is legal), but I feel like adding this feature will not solve it. The notebook is still ambiguous, you can still solve it by following Pluto's reactivity rules in your head, and it still depends on cell order. This is yucky yuck (in both cases) because moving cells should be a no-op.

The alternative solution, which is already possible, disambiguates by making the order explicit!

Current solution

is to name your modifications:

x = [1]

last(x3)

x2 = push!(x, 2)

x3 = push!(x2, 3)

This might seem silly because x === x2 === x3, but it makes the reactive order explicit. Not just for Pluto, but for you or anyone else reading the notebook 😊

(Of course, you can also use static arrays: x = [1], x2 = [x..., 2], etc, but that is not the topic here)

Another example

Before:

write(“file.txt”, “hello”)

read(“file.txt”, String)

After:

begin
    file_written = true
    write(“file.txt”, “hello”)
end

begin
    file_written
    read(“file.txt”, String)
end

For a third example, see the docs for PlutoUI.Button

@dralletje
Copy link
Collaborator

Tried experimenting with Cassette, but pretty hard (and expensive) to find any functions being called with a ! , but that ofcourse doesn't capture all cases.
Also you'd have to track what objects get mutated, because mutation to function local variables wouldn't be a problem etc, etc

@lungben
Copy link
Contributor

lungben commented Oct 29, 2020

One idea would be to check after each cell execution for each global variable if its content changed, e.g. by comparing checksums. This could work for small objects, but would probably take too long for large objects.

Is there any way to leverage the compiler to identify which object is mutated?

@fonsp
Copy link
Owner

fonsp commented Oct 29, 2020

We generally need to know the execution order, hence dependencies, before executing cells.

@chelate
Copy link

chelate commented Feb 14, 2024

Is it possible to provide macro that allows directly annotating dependency? Like

x = [1]

@mutation (x,1) # first mutation 
    push!(x,2)

@mutation (x,2) #second mutation
    push!(x,3)

where the only effect of the macro is to set the Pluto evaluation order? This avoids using up the very valuable symbols x1 x2 etc.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request reactivity The Pluto programming paradigm
Projects
None yet
Development

No branches or pull requests

5 participants