Closed Acmion closed 2 years ago
This seems related to @Araq's more general RFC on type-bound procs which I'm looking forward to: https://github.com/nim-lang/RFCs/issues/380.
@n0bra1n3r Yeah, good catch!
As the issue states, operators are even more problematic than standard procs.
Just copying what other major programming language do to Nim doesn't seems good idea unless there is a good reason.
All those who have experience with other programming languages and are learning Nim could benefit from this.
For people who is not familiar with these feature, that just makes learning Nim harder. Also adding new features makes language spec complicated and maintaining Nim compiler harder.
Currently procs operating on objects will always populate the definitions of the current module, even if this is not always necessary nor wanted. As such, intellisense will start suggesting a lot of stuff, even if some of it may be completely impractical (for example, objects that have complicated "constructors"). Not importing these procs is not an option, because otherwise dot notation will not work at all.
If a module has so many procs and you want to import a few of them because importing them all cause problem, I think you should split the module to smaller multiple modules.
Even if you can bind procs to a specific type, from module import Book
or from module import Book.*
can import many unused procs if the imported module defines many procs that are bound to Book
object type and you use only a few of them, isn't it?
Having less definitions makes reasoning about code easier. Having less definitions makes certain bugs easier to detect (especially since overloading is possible)
Can your RFC reduce a number of procs need to be implemented? Isn't it just make easier to reduce a number of imported procs?
Some procs have quite general names and can thus be confused with other procs within the current module.
tables module defines multiple types (Table
, OrderedTable
, CountTable
) and it defines multiple general name procs (add
, len
, del
, etc).
There are also add
, len
and del
procs for seq type.
Can these same name procs be confusing?
I can use these procs without problems:
import tables
var t = {'a': 5, 'b': 9, 'c': 13}.toTable
t.del 'a'
echo t.len
var s = @[0, 1]
s.del 0
echo s.len
var ct: CountTable[char]
ct.inc 'a'
ct.inc 'b'
ct.del 'a'
echo ct.len
Even if there are same name and same parameter type procs in different module, you can disambiguate a call by adding module name like modulename.procname()
.
(But I don't think having mutiple procs with same name and same parameter types in different modules are good idea.)
After you wrote following code, when you write a.
, your intellisense should suggests only procs that has Table type as first paramter.
import tables
var
a = {1: "one", 2: "two"}.toTable
Anyway, If books.nim defines proc was_released_before_or_during_1970*(this: Book): bool =
and it is bound to Book
ref object type and example.nim also defines same name proc and need to import Book
type, your RFC still doesn't seems to solve the problems.
More or less a duplicate of https://github.com/nim-lang/RFCs/issues/380
Procs Bound Exclusively to Objects
Abstract
Some procs should optionally be bound exclusively to objects. In practice this would mean that certain procs would only be accessible via object dot notation, rather than accessible directly from the current module.
This could make type imports more convenient and more like how other popular languages do it. This would also clean up the list of current definitions within the current module.
Motivation
Description
There should be an option to bind procs directly to a specific type and not just leave them as "unbinded" procs. Currently procs operating on objects will always populate the definitions of the current module, even if this is not always necessary nor wanted. As such, intellisense will start suggesting a lot of stuff, even if some of it may be completely impractical (for example, objects that have complicated "constructors"). Not importing these procs is not an option, because otherwise dot notation will not work at all.
Object fields can already not be accessed without the instance and dot notation.
These procs could also be callable via the type itself and would thus act akin to static methods in C#.
Alternatively, this could be added as an option to the import command, where
from module import Book.*
(note the .*) would import all related procs toBook
, but only via dot notation. This would remove the need for cases such as:from module import Book, Book_proc_0, Book_proc_1, ..., Book_proc_n
Implementation alternatives:
from module import Book.*
.Downsides:
Examples
Before
books.nim:
example.nim:
example_alt.nim:
After
Note: changes marked with
#####
books.nim:
example.nim:
example_alt.nim:
Backward incompatibility
This would depend on the implementation.
Other
A discussion regarding the problems with code completion when using unbinded functions in Julia.
Even if this would not be implemented in its entirety, I believe that the "augmented import command" could be worth considering.