wren-lang / wren

The Wren Programming Language. Wren is a small, fast, class-based concurrent scripting language.
http://wren.io
MIT License
6.87k stars 552 forks source link

List/Map Attributes #1130

Closed mwasplund closed 1 year ago

mwasplund commented 1 year ago

Could an attribute on a class have map or list values?

#extension = ["value1", 1, true, 2.5]
class MyClass {
}
ruby0x1 commented 1 year ago

The docs are here just in case, I think a group already behaves like you want?

mwasplund commented 1 year ago

Yes, you could fudge a group to pretend to be a list or map, however I interpreted them as a logical grouping of keys. In my case I was actually thinking of using a single group to provide a collection of properties for a class with some of them being lists themselves.

#extension(before = ["Ext1", "Ext2"], isEnabled = false, after = [ "Ext3" ]
class MyClass {
}

If groups are meant to be maps/lists, why not just use the existing syntax?

#extension = { "before": ["Ext1", "Ext2"], "isEnabled": false, "after": [ "Ext3" ] }
class MyClass {
}
ruby0x1 commented 1 year ago

It's a simplified form of an ECMA standard.

When using a tool the way it's designed it's not really fudging anything. The tool provides a way to store multiple values in the same container, which sounded like what you're after.

As with most things in wren there's a trade off with simplicity and the minimal nature of the language. The attributes provide a wide range of expressiveness under a small simple set of rules which align with the goals

PureFox48 commented 1 year ago

Have you considered using a static indexer rather than an attribute?

class MyClass {
    static [key] {
        if (!__props) __props = {"before": ["Ext1", "Ext2"], "isEnabled": false, "after": ["Ext3"]}
        return __props[key]
    }

    // blah
}

System.print(MyClass["before"])     //> [Ext1, Ext2]
System.print(MyClass["isEnabled"])  //> false
System.print(MyClass["after"])      //> [Ext3]
System.print(MyClass["whatever"])   //> null
mwasplund commented 1 year ago

@ruby0x1, thanks for the answers. I was incorrectly understanding what the purpose of a group was. I think the method like signature threw me off. It felt odd that the language already had a built in concept of lists and maps and introduced a merged concept of groups for attributes. 🤷

@PureFox48, I think I am going to land on something similar to your proposal. A simple static getter should let me attach a list to a class object nicely.

ruby0x1 commented 1 year ago

Small note worth mentioning about the attributes is they also stack. See below, they come out as a list for before and after as well.

#before = ext1
#before = ext2
#isEnabled = false
#after = ext3
#whatever
class Example {}