Comments (8)
Minimal example to test with default value, and then without.)
setvar mydict = {}
echo passed variable before:
= mydict
echo
proc a(; input={} ) {
#func a( input={} ) {
echo "input:"
= input
echo
setvar input['a_added'] = 'something'
}
a (mydict)
#var dump
#setvar dump = a(mydict)
#echo retured:
#= dump
#echo
echo passed variable after:
= mydict
echo
from oil.
Thanks for posting the 0.19.0 blog article it provided some good context around the "Default values can't be mutable" part here. (I will move the second part to a different issue.)
https://www.oilshell.org/blog/2024/01/release-0.19.0.html#background
We disallow mutable default args, a well-known wart in Python
Uh, so I didn't know that one, as I don't know writing Python. I didn't know that official gotcha https://docs.python-guide.org/writing/gotchas/
The consequence from that python behavior though, which is from evaluating defaults into a var on func definition and then keep references that variable, looks awful to me: What are those (cosmetic) function signature defaults good for, when in practice, they can only be set to None and get used as a mere switch for a re-computation and assignment within the function, which is thus always required, anyway.
YSH's current corresponding strict disallow rule, is understandable with that background, but that ugly python background rather calls for a proper fix in YSH. (The old python way of using pseudo None defaults will still work.)
It seems to me python is mixing things that need to be separated.
What Python implicitly does for each default value seems to be creating a mutable global (The gotcha doc mentions it can be “exploited” (excusingly: used as intended) to maintain state between calls of a function.)
What do you think about these options:
- calculating the default on call time (as ruby)
- copying the value into a new proc/func local var
- allowing to specify an =(expression)
- specifying a place as default in the proc/func definition could still allow using a centrally mutable global default
from oil.
Maybe the gotcha that exists in python with mutable defaults can also be solved nicely by explicit syntax that distinguishes between pointing to some variable default and assigning an explicit on one at each call time (state=->dict, init={}).
Also see example in "=-> as explicit "pointer assignment" for mutables?" #1796
from oil.
So the Python-like workaround is
func f(arg=[]) { # BAD
echo
}
func f(arg=null) {
setvar arg = arg or []
}
We probably should document that somewhere, not sure where ... but Python programmers may know it
maybe in the FAQ
from oil.
Of course document workarounds in the error message that forbids mutables. :-)
from oil.
AFAIU the python workaround could continue to work, even if ysh explicitly distiguishes between assigning defaults by value withparam=default
and by reference pointers withparam=->default
explicitly.
from oil.
Ok, mentioning in the strict error message the workaround to set a default =null + setvar param = param or []
can work for now, but it's still a wart, and seems fixable as of the overview in: #1793 (comment)
from oil.
Of course documenting would depend on the solution found.
Which could make the problem smaller, or even disappear when removing the [EDIT: in-]consistent semantics for different variable types (i.e. require '->' for mutables, and using value.place for them, to allow to re-bind for all aliasing semantics by default.)
from oil.
Related Issues (20)
- Error message shows wrong/confusing position for long commands HOT 3
- command -v "$emptyvar" returns zero HOT 3
- Oils 0.23.0 TODO
- Missing "Str=>lower()"
- Abort with += on missing dict key
- intermittent crash running amd-test script -- reproducible in dbg, opt HOT 4
- OpenBSD doesn't have RLIMIT_AS
- Add pp [x + 42] to print an expression and its value - like Rust dbg!() HOT 2
- github URL pastebin HOT 8
- bash allows pasting multi-line code snippets, but OSH/YSH don't HOT 3
- allow backspace from multiline expressions HOT 1
- allow any custom prompts HOT 2
- typeof / reflection / assign results of '=' HOT 3
- emoji/unicode identifiers
- Setting up GNU readline history HOT 1
- 'view latest' released version in documentation - because old links are often surfaced HOT 1
- crash in parsing return HOT 1
- BashArray could have a sparse representation (ble.sh)
- bash SHELLOPTS and BASHOPTS support
- pitfall - IFS= read x doesn't set x (read --raw-line or for <> loop instead) HOT 6
Recommend Projects
-
React
A declarative, efficient, and flexible JavaScript library for building user interfaces.
-
Vue.js
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
-
Typescript
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
-
TensorFlow
An Open Source Machine Learning Framework for Everyone
-
Django
The Web framework for perfectionists with deadlines.
-
Laravel
A PHP framework for web artisans
-
D3
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
-
Recommend Topics
-
javascript
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
-
web
Some thing interesting about web. New door for the world.
-
server
A server is a program made to process requests and deliver data to clients.
-
Machine learning
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
-
Visualization
Some thing interesting about visualization, use data art
-
Game
Some thing interesting about game, make everyone happy.
Recommend Org
-
Facebook
We are working to build community through open source technology. NB: members must have two-factor auth.
-
Microsoft
Open source projects and samples from Microsoft.
-
Google
Google ❤️ Open Source for everyone.
-
Alibaba
Alibaba Open Source for everyone
-
D3
Data-Driven Documents codes.
-
Tencent
China tencent open source team.
from oil.