ID:329787
 
There has been a discussion about namespaces in DM, and the usage of parent_type. Since Lummox is currently the primary developer of the BYOND engine/language, and presumably has respectable experience with the relevant languages, I would appreciate his input on these matters.
Namespaces make sense in a library perspective, but I'm not convinced they have any real value in a regular project.

Essentially the best DM library developers already operate this way, by sticking as much as they can into a datum and avoiding too many globals. Datums are an effective way of using all the benefits of namespaces, so I don't think adding namespaces internally would be of much benefit.

There also is the question of scope resolution I suppose, but it doesn't come up enough in DM to be an issue. It also means getting into deep layers of the compiler.
Type1
parent_type=/obj
Type2
parent_type=/datum
//What about using parent_type to do something like that?

Also, do namespaces not essentially provide "global" variables/functions within that namespace? Something you would have to instantiate a /Library datum to get access the same features in DM? ie:
using namespace
namespace::Function()
//vs
var/Library/libraryDatum=new
libraryDatum.Function()
In response to Falacy (#2)
Falacy wrote:
Also, do namespaces not essentially provide "global" variables/functions within that namespace? Something you would have to instantiate a /Library datum to get access the same features in DM? ie:
> using namespace
> namespace::Function()
> //vs
> var/Library/libraryDatum=new
> libraryDatum.Function()
>

Not necessarily. Many (maybe most?) languages require static methods on a class for something like this to work.
In response to Falacy (#2)
Namespaces not only provide a way to group objects into namespaces, they provide a way to tell the compiler which namespaces you're using. Having namespaces lets you avoid naming collisions (in java there is a java.util.Date object and a java.sql.Date object). Being able to tell the compiler what namespaces you're using lets you still refer to the objects by just their class name. In Java you could reference a Date object either of these ways:

java.util.Date date = new java.util.Date();

import java.util.Date;
Date date = new Date();

DM's parent_type isn't the equivalent of namespaces. It lets you put things in a namespace but it doesn't let you declare what namespace you're using. You can use parent_type to define something like this:

ForumAccount
DynamicLighting
LightSource
parent_type = /obj

Which makes an obj called LightSource in the ForumAccount.DynamicLighting namespace. Since there's no way to tell DM which namespaces you're using, you'd always have to reference it has /ForumAccount/DynamicLighting/LightSource. To actually have namespaces in DM you'd need to be able to do something like this:

import /ForumAccount/DynamicLighting

var/LightSource/lightSource = new()

You also have the same problem with this:

Falacy wrote:
> var/Library/libraryDatum=new
> libraryDatum.Function()
>

This acts like you're putting the Function() proc in a namespace but there's no way to specify that you're using the libraryDatum namespace. You'd have to always refer to it as "libraryDatum.Function()".
I want enums. :D (Don't say "Use a list" or something) ;_;
In response to Ocean King (#5)
Ocean King wrote:
I want enums. :D (Don't say "Use a list" or something) ;_;

It'd need to have compiler support, otherwise I don't see it as being any different from using constants.

var
enum/suit = enum(DIAMONDS, HEARTS, SPADES, CLUBS)

card
var
suit/suit = suit.DIAMONDS

Without compiler support there's nothing stopping you from doing this:

card.suit = "14"

So to emulate enumerated types you can just use constants. If you want, you can package them in a global datum like this:

var
Suit/Suit = new()

Suit
var
const
CLUBS = 1
DIAMONDS = 2
HEARTS = 3
SPADES = 4

card
var
suit = Suit.CLUBS