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

Support const within classes #1243

Open
luis-soares-sky opened this issue Jul 3, 2024 · 3 comments
Open

Support const within classes #1243

luis-soares-sky opened this issue Jul 3, 2024 · 3 comments

Comments

@luis-soares-sky
Copy link
Contributor

It would be nice to have class-scoped consts which don't pollute the global scope.

const THIS_IS_GLOBALLY_AVAILABLE = "abc"

class Abc
    const A_LOCALLY_SCOPED_CONST = "def"

    function getMeAValue()
        return A_LOCALLY_SCOPED_CONST
    end function
end class

print THIS_IS_GLOBALLY_AVAILABLE         ' > "abc"
print new Abc().getMeAValue()            ' > "def"
print new Abc().A_LOCALLY_SCOPED_CONST   ' > invalid
print Abc.A_LOCALLY_SCOPED_CONST         ' > invalid (I think)
@TwitchBronBron
Copy link
Member

TwitchBronBron commented Jul 3, 2024

In other languages like C# and VB, classes have a static modifier that makes them available on the class itself, and readonly to be modifiable only at initialization (essentially what we do with const statements). Here's how it's implemented in VB:

class Abc 
    public shared readonly A_LOCALLY_SCOPED_CONST as string = "def"
end class

Sub Main()
    Console.WriteLine(Abc.A_LOCALLY_SCOPED_CONST)
End Sub

My gut leans towards implementing it more like that Here's your example modified in a similar way:

const THIS_IS_GLOBALLY_AVAILABLE = "abc"

class Abc
    static const A_LOCALLY_SCOPED_CONST as string = "def"

    function getMeAValue()
        return Abc.A_LOCALLY_SCOPED_CONST
    end function
end class

print THIS_IS_GLOBALLY_AVAILABLE         ' > "abc"
print new Abc().getMeAValue()            ' > "def"
print new Abc().A_LOCALLY_SCOPED_CONST   ' > invalid
print Abc.A_LOCALLY_SCOPED_CONST         ' > "def"

Thoughts on this?

@luis-soares-sky
Copy link
Contributor Author

I like that version more 😄 although we'd be introducing a static keyword which doesn't mean much outside the scope of this change. Does that make sense? Should const inside a class just act as a static instead?

@pawelhertman
Copy link

pawelhertman commented Jul 12, 2024

I like the idea of introducing static values (also, not mentioned, static functions)!

I'll refer to TypeScript, as this is my background - in the process of TS transpilation, constant values aren't replaced with direct values, they just follow JS const concept. So this is something specific to Brighterscript as it's a performance optimization for Brightscript. We can say that in Brighterscript the keyword const means replacing all such variable references with the value in the transpiled code.

Once we have it defined this way, there is no sense of just const inside an instance of class as it doesn't exist in the transpiled code. But it does make sense if we introduce the static concept representing the uninstantiated class. It would actually work exactly as a namespace, just with a lower-level assignment, just for better code organisation. In a normal non-STB world, where there is no need for such heavy performance optimisations, it would be a static property assigned to the class.
Because of introducing the static keyword, I would take advantage of the opportunity and introduce static methods too. I'm just writing a code that builds an instance simulating such a concept and had to use the namespace for this:

namespace AppLog
  enum Severity
    INFO = "info"
  end enum

  class Log
    severity as AppLog.Severity
    sub new(severity as AppLog.Severity) : m.severity = severity : end sub
  end class

  function info() as AppLog.Log : new AppLog.Log(AppLog.Severity.INFO) : end function
end namespace

The inspiration was the JavaScript world where you can create e.g. a Date instance using e.g. the Date.now() static method. With the static constants and methods concept in Brighterscript it could look like this:

class AppLog
  static const SEVERITY_INFO = "info"

  static function info() as AppLog : new AppLog(AppLog.SEVERITY_INFO) : end function

  severity as String

  sub new(severity as String) : m.severity = severity : end sub
end class

TypeScript too doesn't support enum as a static property. There is a workaround defining a namespace and a class with the same name which, in my opinion, should be possible in Brighterscript too:

namespace AppLog
  enum Severity
    INFO = "info"
  end enum
end namespace

class AppLog
  static function info() as AppLog : new AppLog(AppLog.Severity.INFO) : end function

  severity as AppLog.Severity

  sub new(severity as AppLog.Severity) : m.severity = severity : end sub
end class

Actually, by letting declaring a namespace and a class with the same name, there wouldn't be a necessity for implementing the static thing

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants