Re: NEWBIE - generics issue

2018-07-20 Thread LeuGim
I get no compiler error for your example (maybe there is some problem in your 
full code), just a run-time error from dispatcher, because you didn't allocate 
the object for `a` (via `new`, as the variable is of reference (pointer) type, 
not object itself). The full code:


type
  Something = object
a: int
special: Special
  
  Special = ref object {.inheritable.}
  SpecialisedTA = ref object of Special
abc: string
  SpecialisedTB = ref object of Special
def: string

import json

method foo(s: Special, node: JsonNode) {.base.} = assert(false, "Kinda 
abstract")
method foo(s: SpecialisedTA, node: JsonNode) =
  s.abc = node["abc"].getStr()
method foo(s: SpecialisedTB, node: JsonNode) =
  s.def = node["def"].getStr()

var a = new SpecialisedTA
var jsonNode = parseJSON"""{"abc": "5", "def": "7"}"""
echo jsonNode
foo(a, jsonNode)
echo a.repr


Run

Wrapping your code in posts with "```nim" and "```" makes it highlighted.


Re: Macro - whileSome: none:

2018-07-20 Thread LeuGim
If you want the second keyword be "none" and not "do", you can use 2 
templates/macros and a variable to pass state between them, like:


var whileSomeNone: bool
template whileSome*(condition: typed, body: untyped) =
  whileSomeNone = condition
  if whileSomeNone:
while true:
  body
  if not condition: break
template none*(body: untyped) =
  if not whileSomeNone:
body


Run

No check is performed here that `none` follows `whileSome`, as downside.

May be used nested: 


import whilesome

var a = 3 # set to >=7 for "none" branch
var b = 7
proc c: bool =
  return a < b
whileSome(c()):
  echo a
  inc a
  var i = 0 # set to >=3 for "none" branch
  whileSome(i<3):
echo "i=", i
inc i
  none:
echo "i >= 3 initially!"
none:
  echo "No items to display!"


Run


Re: NEWBIE - generics issue

2018-07-21 Thread LeuGim
`when` is resolved at compile-time, at run-time you get just one of two 
branches, which already knows what field to read from JSON and where to put it. 
So if you explicitly pass strategy (type disambiguator) as compile-time known 
(static) argument, a proc with `when` is the simplest and most performant way.

With those `foo` 's, in my example above `Something` type was not used and the 
variable was of a specialised type, so methods can be replaced with just procs 
too.

You'll need methods if you want variable of a general (`Something`) type and no 
explicit disambiguator:


# using the code from previous example with `foo`'s, except the last 
paragraph

# prettifying echo'ing
method `$`(s: Special): string {.base.} = assert(false, "Kinda abstract")
method `$`(s: SpecialisedTA): string = "[abc: " & s.abc & "]"
method `$`(s: SpecialisedTB): string = "[def: " & s.def & "]"
proc `$`(s: Something): string = "[a: " & $s.a & ", special: " & $s.special 
& "]"

var jsonNode = parseJSON"""{"abc": "5", "def": "7"}"""
var a: Something
a.a = 3
a.special = new SpecialisedTA
# `a` can store either `SpecialisedTA` or `SpecialisedTB`,
# and you don't pass any explicit disambiguator to `foo`
foo(a.special, jsonNode)
echo a# => [a: 3, special: [abc: 5]]
a.special = new SpecialisedTB
foo(a.special, jsonNode)
echo a# => [a: 3, special: [def: 7]]


Run


Re: Globally-invoked macros

2018-07-22 Thread LeuGim
> they make semantics clear in one place in the source code

For this reason per-module macros invocations should maybe be restricted to the 
top of the module (as `#? strongSpaces` is now), with only imports and static 
code allowed before them: the user anyway has to look at the module's top for 
imports, to know how to read/understand the module's code. But anyway for now 
imports are allowed throughout the modules, to read a part of it the user has 
to look through all preceding top-level code. The proposed per-module macros 
are supposed to be invoked only at the top-level too, not much difference with 
imports.

> Who gets to dine first?

The macros are invoked in the order in which their invocations follow, the user 
is in full control, the macro's author doesn't and shouldn't decide this. It's 
the same with today's per-block and per-routine macros, again no difference.


Re: Globally-invoked macros

2018-07-22 Thread LeuGim
Your points are generally correct, just don't fit to Nim as it is - they are 
not satisfied already.

> Imports just add symbols from other modules to a module

Not in Nim.

You yourself already mentioned converters - code starts to work differently 
just by importing a module.

Add to this methods - just by importing a module you change dispatching, 
already existing calls take different paths, it's not mirrored in your code. 
But why methods - just regular procs do the same, you can add a better (more 
specific) overload match by an import and change logic of an alredy working 
code. I.e. you don't add any calls for it - just an import.

Concepts: their matching is changed by just adding symbols.

`mixin`: new symbols are taken into account, just their adding changes how the 
code works. Changes may be not less at all, than with per-module symbols, the 
latter just adds a friendly syntax.

Scarcely these are all the features that change program's logic just by 
addition of symbols. These all of coarse lessen code's evidence, for that 
increasing its expressiveness, and so far the latter is Nim's virtue.


Re: Globally-invoked macros

2018-07-22 Thread LeuGim
Btw, there are nice hints for term rewriting macros on their matches in 
compiler output, the like may be displayed for such macros, adding a bit 
explicitness.


Re: Globally-invoked macros

2018-07-22 Thread LeuGim
> As for term rewriting macros: AFAIK they are meant for local optimization and 
> code adaption, not for behavioral changes.

But they still can say turn _2_ to _3_. :) And these macros too are not meant 
to change behaviour counter-intuitively (why would one want?), say in the  
@quelkef's example - just to introduce cleaner/saner (subjectively), 
non-repetitious recursion syntax.

By efficient is rather meant, that it produces binaries not less performant, 
than C's, and programmers efficiency much comes from expressiveness, but well. 
:)

* * *

I put it not clear in that post, those features, affected by currently defined 
symbols, are much more implicit, than this one - they are applied automatically 
just by import itself, you don't have any triggering code in your module. And 
these per-module macros are applied manually, you see them in the module, at 
least prior to the place, where they are applied, or closed to module's top, 
with that restriction in force. So this feature is much more obvious, it's 
rather on par with imports and filters.


Re: Globally-invoked macros

2018-07-22 Thread LeuGim
Another (a more explicit) way would be to have possible to deal with modules 
the same as with routines or blocks in macros, and to have a `currentModule` 
symbol. Then the same could be expressed with `a.implementRecur currentModule`, 
with the usual syntax, the same as `a.implementRecur: ...` (for blocks) and 
`a.implementRecur someProc`.


Re: Globally-invoked macros

2018-07-23 Thread LeuGim
> I think that'd be strange; ... I think that'd be strange; ... It feels like I 
> should end up with the macro output followed by the original 20 lines of code.

Yes, `wrapWith` looks more intuitive.


Re: Globally-invoked macros

2018-07-23 Thread LeuGim
> Which one is it, more obvious than imports or on par with them? You just 
> reminded me that imports can change the behavior of local code

It is more obvious than features are listed in one of my previous posts (i.e. 
converters, overloads, concepts, `mixin`, term-rewriting macros) - they all are 
enabled just by an import, you don't switch them on even by a single line of 
code in the module, which they change. They are on par with imports (imports 
themselves, not those other features triggered by them) and filters, in that 
they both are represented by a single line in the module which they change (are 
visible to the user). 


Re: Globally-invoked macros

2018-07-24 Thread LeuGim
Say you're using [NimContracts](https://github.com/Udiknedormin/NimContracts). 
You add `import contracts`, then yet for any procedure using it you add the 
pragma `contractual` (but quite probably most procedures in the module will 
need it), or wrap blocks of code in `contractual:` with indentation. Yet the 
features of NimContracts are used by introducing inner blocks with `invarinat`, 
`ensure`, `body`, `require`, they are visible already, `contractual` there's 
usually needed only technically, not as a hint for the user.

This is probably the same with most the like libraries, that is those, which 
need surrounding context for their features to work.


Re: Proposal for Forum Improvements

2018-07-25 Thread LeuGim
Answered at GitHub.


Re: Globally-invoked macros

2018-07-26 Thread LeuGim
> I realized that there's no technical reason to disallow wrap statements from 
> appearing in any statement list

Yes, it may be of much use. Say, though to wrap a procedure's body in a macro 
you can wrap the procedure itself with a pragma and in the macro to get its 
body, the macro may be of general use and expect just a statement list; and you 
then required either to modify the macro code and introduce a special case 
(much undesired), or to introduce an intermediate macro. Yet there are 
statement lists for `if`, `while`, ...

> Wrap statements are allowed after templates and macro definitions so that a 
> wrap statement may use a macro located in the same module as it appears in

I think compile-time procedures, constants and `static` blocks (all the 
compile-time stuff) should be allowed too, they all may be in the required 
background for the macro.

> so that `body.macro(arg)` can be idiomatically used

No, such macrso are usually called `macro(arg): body`, so your proposed order 
is optimal.

> If anyone can think of anything good

`processwith` is closer in meaning, though longer.


Re: Globally-invoked macros

2018-07-26 Thread LeuGim
I'll try. :) Sorry, it then becomes long.

Situation: one has macro, which takes a statement list, and a procedure, which 
body (contents) needs to be processed with that macro:


macro m ...
# it can be used so:
m:
  echo "smth"
  doSmthElse()
proc p =
  ... # We want to apply `m` to these statements


Run

Instead of this


macro m ... # expects a statement list as the argument
proc p =
  wrapwith m
  ...


Run

one can principally do


proc m2 ... # rewritten to take a procedure as the argument
proc p {.m2.} =
  ...


Run

. But if `m` is not created for this specific use (to process `p`), but 
imported from somewhere, or is used already for blocks of code (`m: ...`), then 
it cannot be just changed to take a proc instead. Even if it's newly created, 
making it to work with both


proc p {.m.} = ...
# and
m:
  ... # stmtList


Run

is a complication.

One can instead write yet another macro, which takes `p`, gets its body and 
passes it to `m`, which is again an extra burden for user.

So, then, if `wrapwith` is allowed within inner levels, including inside procs, 
then one can just use an existing macro, which takes a statement list (i.e. is 
supposed to be used as `m: stmt1; stmt2`), or write just one macro for both 
cases, expecting just a statement list in it:


import theModuleWithThatMacro
m:
  echo "a statement"
  echo "yet another"
proc p = # {.m.} would not work, `m` doesn't expect a proc
  wrapwith m
  echo "m gets this statement"
  echo "together with this, in a statement list"


Run

So +1 for allowing in any statement list.


Re: Winim - Nim's Windows API and COM Library

2018-07-26 Thread LeuGim
Much thanks for the new version!


Re: Why is it needed to discard void return value from c function?

2018-07-28 Thread LeuGim
You can call them without `()`, when it's clear otherwise, that it's a call. 
Say, in command syntax with arguments: `a b` (means `a(b)`). In dot syntax: 
`b.a`.

In just `a` on its own `a` represents just the proc itself, so that you can 
send it as an argument to other procs or save to a variable, like: `mySeq.map 
toUpperAscii`, `toUpperAscii` is not called here, but passed to `map`. Or:


proc x(s: string) = echo "[", s, "]"
var y = x
y "z"


Run

And as just `quit` returns the proc itself, it is an expression ('None' is its 
type), not a statement.


Re: Return SUM types from proc

2017-01-25 Thread LeuGim
Supports, if the sum type can be treated as generic, i.e. if compiler can 
decide at compile-time for each use of the sum type, which concrete type will 
it substitute. Like in using such a proc:


proc test(arg: static[int]):Ret =
  when arg < 0:
return A(a_value:arg)
  else:
return B(b_value:arg)


But the argument, on which the type choice is made, is static, that is, 
compile-time: really 2 different zero-argument procs will be instantiated by 
compiler for `test(10)` and `test(-5)`, and their arguments should be able to 
be evaluated at compile-time.


Re: Should/can we get explicit concepts?

2017-09-02 Thread LeuGim
Neither a feature or a bug. 

These are just different ways of abstraction, each of which can be preferrable 
in some situation. I like concepts (that is, implicit ones, as they are) too, 
I'd not want them just to be replaced with interfaces (explicit concepts), the 
proposition is of having both ways. The purpose of interfaces is to express 
programmer's intention; not what concepts are intented to.

About Go's interfaces: I don't know this language, I just heard that something 
very different is called by interfaces in it, just sharing the same word; 
probably it's something nearer to concepts; better not to compare things as 
respective just because of wording, this is why I've mentioned explicitly 
Delphi (Object Pascal), Java, PHP and C# (probably there are more) as having 
this feature.

Still there is some difference between interfaces in those languages and 
explicit concepts, as proposed for Nim: those are based on dynamic dispatch; 
this not what really needed, procs can be instantiated statically per concrete 
type, the same as with implicit concepts (as now). So they are still the same 
concepts in all respects, except:

  * they don't match types, which were not declared explicitly as satisfying 
these explicit concepts;
  * obviously, there is a way to declare for a type, that it satisfies some 
explicit concept, like proposed `satisfies MyConceptName` in type declaration, 
or it can be `implements`, or a pragma (`{.satisfies: MyConceptName.}`);
  * obviously, some addition in concepts syntax, to mark it as explicit: again, 
proposed `explicit` before `concept` keyword, or a separate keyword 
`interface`, or a pragma (`type X = concept {.explicit.}`).




Re: proc(t: typedesc): var t -- expected 'None' error

2018-03-27 Thread LeuGim
I don't know how to make it work with `: var t`, maybe a bug or not supported; 
works with `template getMutableVal(key: int, t: typedesc): var typed =`.

I assume you need `0.getMutableVal(bool) = false` syntax, otherwise you can 
pass types as a generic parameter (`proc getMutableVal[t]...`), that works with 
`: var t`.


Re: Mutability of loop variables

2017-01-12 Thread LeuGim
You can no way modify the string via this iterator. The easiest way: split it 
into a sequence via the same-named proc (just save it into a variable), and 
then in the `for` loop use `mitems` iterator on it, it allows modifying. Then 
`join` the sequence into a new string.

Or w/o modifying: use a variable in the loop (`var s=line.strip`), do any 
processing, then concatenate into a new string, defined empty before the loop.

To syntax-highlight Nim code in the forum posts wrap it like in the hint below 
the textarea.


Re: Windows Subclassing

2016-07-23 Thread LeuGim
Like that:

`someType(someValue)` (or, what's the same, `someValue.someType`) means 
"convert this value to this type", and compiler should consider these types 
(that of the value, and to which you convert) as compatible to allow this 
operation, and it can use an additional transformation for this (you can define 
it creating a `converter` for these types).

`cast[someType](someValue)`, on the other hand, means just "interpret this 
value (its bits sequence) as being of such a type"; it doesn't involve any 
compatibility-checks nor transformations of the value - you relief the compiler 
of responsibility for validity of type change; so you can convert between 
formally incompatible types - just make sure, that the cast really makes sense 
(as in this instance - one type is pointer, the other - a procedure - is really 
a pointer too).

I think you can find it in the manual, and possibly it's better described there.


Re: Bug with generic methods?

2017-09-04 Thread LeuGim
> Please note the biggest problem of inheritance-based interfaces: you cannot 
> add one to a type already in existence when you define the interface

Certainly you cannot; that is the point - not interfaces state, what types 
satisfy (implement) them, but the other way round, types state, what they 
implement, and interfaces can only restrict, what types can state that (say, 
providing signatures for required procs); not satisfying the interface's 
restrictions results not in rejecting for the type to be considered as being of 
that interface, but in a compile-time error. E.g., supposing concepts-syntax 
for interfaces:


type
  I = interface x
p(x)
  T = distinct int implements I
# p(t: T) = discard


This should result in a compile-time error, unless the last line is uncommented.

And at the same time


type
  I = interface x
p(x)
  T = distinct int
proc p(t: T) = discard
echo T is I  # -> false


, because `T` here is not intended to be `I`.


Re: Wrong indentation in IF expr

2017-04-11 Thread LeuGim
Probably expressions are intented to work with indentation too, so probably 
will do some day, so parantheses and semicolons then are just a practical 
workaround for now, so aren't documented.


Re: Are array types that differ only in index boundaries different?

2017-09-26 Thread LeuGim
Not a run-time conversion is meant (that there are given 4 bytes for "3" and 
then at run-time it's transfered into 1); just the type for `3` literal is 
`int`, and of the value, created from it for x, is `int8`. And that "treatment" 
is implicit. ׃) You expressed it more exactly.


Re: Containers of generic types

2017-09-14 Thread LeuGim
Probably you're asking about what here is discussed: 
[https://forum.nim-lang.org/t/3150](https://forum.nim-lang.org/t/3150); that 
is, on storing different (concrete) type values in one container. You have to 
choose between casts, object variants, refs to objects + dynamic dispatch 
(methods), maybe something else, depending on your task. Just generics/concepts 
by themselves cannot be instantiated and so stored in containers, because of 
not having any run-time representation (not just now, it cannot be otherwise).

With just creating generic containers, storing values of one type for each 
instantiation, there's nothing special to do: just `type MyContainer[T] = 
seq[MyObject[T]]` and the like.


Re: Do notation without parentheses

2017-06-07 Thread LeuGim
I tested with 0.16.1. With current 0.17.1 indeed the last example compiles, and 
the first fails with redifinition. So now `do` means something different, I 
don't know what. May be a bug, maybe a special case of blocks with no new 
scope. Otherwise blocks open new scopes, and this for example did compile and 
still does now:


block:
  var x = 1
  echo x

block:
  var x = 2
  echo x



Re: Been away for 9 months. What changed? Need some help to get back on track.

2017-08-26 Thread LeuGim
> better concept system from @zahary?

Yes, [docs](https://nim-lang.org/docs/manual.html#generics-concepts) (except 
VTRef).


Re: Custom memory allocator and memory region

2017-09-09 Thread LeuGim
While direct support for seqs and strings is not here (it's planned, according 
to the manual), you can wrap them in objects.


type
  MySeq[T] = object
data: seq[T]
  Cuda = object

var foo = cast[ptr[Cuda, MySeq[int]]](alloc sizeOf(MySeq[int]))
foo.data = newSeq[int]()

foo.data.add 7
echo foo.data[0]


or with constructor and wrapped procs


proc newMySeq[T](size = 0.Natural): Cuda ptr MySeq[T] =
  result = cast[ptr[Cuda, MySeq[T]]](alloc sizeOf(MySeq[T]))
  result.data = newSeq[T](size)
proc add[T](s: Cuda ptr MySeq[T], v: T) = s.data.add v
proc `[]`[T](s: Cuda ptr MySeq[T], i: int): T = s.data[i]


for more convenient usage


var s = newMySeq[float]()
s.add 5
echo s[0]



Re: Convert tuple into a Object

2017-09-01 Thread LeuGim
Why they should be truncated, if they are of the same size?

And your macro assigns fields by names... That is, it in the end doesn't allow 
you to write like `createRef(O, (5, 6.6, 7i8, 8i8))`, just providing a type and 
values.


Re: Differences: Object variant vs static conditional fields

2017-09-06 Thread LeuGim
To store defferent types values in one seq with no (when values are of the same 
size) or minimal memory overhead, and no CPU overhead, one has to use casts 
(`cast[]()`), obviously at the coast of non-distinguishing their types; that 
is, it just has to be known, at what index what type is used, or items have to 
be used disregarding their types (say, for storing in files, as is). Runtime 
type differentiation necesarily involves overhead, generally nothing less than 
with object variants.


Re: Convert tuple into a Object

2017-09-01 Thread LeuGim
An unsafe but fast and clean way - just to cast your tuple to your object type:


proc createRef(typeinfo: typedesc, data: tuple): auto =
result = new(typeinfo)
result[]=cast[typeinfo](data)


Be aware you should provide a tuple of values of needed types, or the same in 
size, and not just compatible:


type
  O = object
x: int
y: float
z: int8
q: int8

let r = createRef(O, (5, 6.6, 7i8, 8i8))
echo r[]


In this example, if you provide the 3rd as `int`, not expected `int8`, you 
won't get the 4th item of tuple into your object - `7` literal will pass an 
`int` value (32/64 bits), setting `z` and `q` fields to `7` and `0` 
respectively.


Re: Partial casing is foo_bar

2016-07-19 Thread LeuGim
_OderWat:_ {. pure .} could be used for the enum in your example, no renaming 
then needed.

* * *

I'd like some special character to be allowed at the end of identifiers, be 
that underscore, or (better) apostrophe (`'`), or something else present on 
keyboards. `x`, `x'`, `x''`, or `x`, `x_`, `x__`, are convenient to use for 
related local variables (apostrophes are easier to distinguish, and don't look 
ugly). And I like style-insensitiveness.

Maybe a per-module directive (pragma) for prohibiting using the same identifier 
in different styles throughout that module could satisfy some of people, who 
have troubles with this. Even with that option enabled the possibility remains 
to use identifiers from other modules (of other authors) in preferred style. 
Say, to use `x_y` from another module as `xY`, given that it's used only as 
`xY` in this module. And the usual behaviour (any style allowed) remains, when 
the option is not enabled.


Re: Containers of generic types

2017-09-14 Thread LeuGim
Storing values of different types in a container, in arbitrary order, and 
handling them then appropriately to their types at run-time, necessarily means 
run-time dispatching (detemining type of each value in the container at 
run-time), that is, something you can program - there's no restrictions on 
run-time behaviour of your programs, made with Nim. At low level, your values 
have to have some type information stored along with them. To not do that 
manually (though you can), there are [object 
variants](https://nim-lang.org/docs/manual.html#types-object-variants) in Nim, 
exactly for this task, the same as in Pascal, or like "struct with union 
inside" in C terms; they use memory for the largest in size of branches, that 
is, use the same storage space for different, even different-sized, values. 
Yet, for objects, you can inherit them from one base type and use 
[methods](https://nim-lang.org/docs/manual.html#multi-methods) instead of procs 
- they distinguish types; this same way run-time dispatched interfaces work. 
These all don't use casts or any unsafe features.

The reason for mentioning casts was that in some cases they allow to manage 
without run-time overhead for this task.


Re: Bitwise operation problems.

2016-11-27 Thread LeuGim
Nothing wrong here with `and`. Probably just what you want is `or` (if you want 
to combine 4 values with disjoint bits into 1).


Re: How to transform compile time into runtime data

2017-07-11 Thread LeuGim
An easy workaround to not add `genericCall` \- passing `procs` as the first 
argument:


# remote.nim, only changes

# making exported
var registeredProcs* {.compileTime.} = newSeq[string]()

# ...

proc genericCall*(procs: seq[string], id: string, x: float): float =
# ...

# user.nim
import remote as remote_module

proc userSquare(x: float): float {.remote.} = x * x
proc userCubic(x: float): float {.remote.} = x * x * x

const procs = registeredProcs

discard procs.genericCall("userSquare", 1)
discard procs.genericCall("userCubic", 1)


Maybe you can make `procs` in `genericCall` bound to the current module's 
symbol, then you can get rid of passing it as an argument.


Re: Bug with generic methods?

2017-08-31 Thread LeuGim
Exactly, and the same for interfaces (in Delphi/Java/PHP,... sence) (it was 
often claimed here that they are of no need for Nim, because concepts are 
better interfaces).


Re: Compile error when wrapper type(...) with template

2017-05-11 Thread LeuGim
The issue with `foo2` and `foo3` is one and the same: when called from a 
generic proc, untyped-arguments templates in them won't be used for type 
annotations. Your `getType` is not used then, so `macros`'s one used, if you 
import it, what you can see by using explicit `your_module_name.getType` \- 
then `import macros` will change nothing.


Re: generic template

2017-10-10 Thread LeuGim
Yes, that makes sense.

This seems to work: 


template constructFoo*[T1, T2](): Foo[T1, T2] =
  implConstructFoo(typedesc[T1], typedesc[T2])



Re: Wrong indentation in IF expr

2017-04-11 Thread LeuGim
If you generate code automatically, then just flooding a little exptressions 
with parentheses may be the easiest way (parenthesize all subexpressions, not 
statements). Yet add semicolons after statements in expressions. E.g. your code 
works in the following version:


proc strsubsmart(s: string, start: int, fl0wlen: int): string =
if start >= 0 and fl0wlen > 0:
  substring(s, start, fl0wlen)
else:
  var slen: int =
strlen(s)
  var trueStart: int = (
if start >= 0: (
  start
) else: (
  var ss: int =
slen+start;
  if ss >= 0: (
ss
  ) else:
0
  )
)
  var trueLength: int =
if fl0wlen > 0:
  fl0wlen
else:
  slen+fl0wlen-trueStart
  substring(s, trueStart, trueLength)



Re: How do fellow new comers deal with optional parenthesis dropping?

2017-07-13 Thread LeuGim
_@RedFred:_ +1


Re: template and proc with same name

2016-07-03 Thread LeuGim
That's not because templates have priority over procs, but because of argument 
types. Say, if you have 2 procs, 1 taking T and another - any (procs cannot 
take expr), then the 2nd (with any) will be called. The same if the 1st (with 
T) is a template, or if both are templates, or if both are templates and the 
2nd is expr. In all these cases not "template vs. proc" determines the choice.

Though it seems to me that T should be preferred over expr as less specific.


Re: Pascal type to nim

2017-10-10 Thread LeuGim
Nim's object variants are from Pascal, they are what you need. Smth like:


Data = object {.packed.}
case b: byte
of 0:  AsChannelStatus01: TChannelStatus01
of 1: AsVoltageList: array[0..127, single]
# ...
else: discard



Re: Community name?

2018-03-02 Thread LeuGim
Nimians. Sounds like a nation. Nimrodites. Nimologists - only for coredevs. 


Re: template/generic instantiation from here

2017-01-12 Thread LeuGim
This hint should accompany some error message. But the example works well for 
me (no such message).


Re: Should/can we get explicit concepts?

2017-09-02 Thread LeuGim
Yes, seems to be mostly fixed. That time I could not create (or populate) 
dynamically allocated values at compiletime, like sequenses, tables, ptr/ref'ed 
values. As I've just tested, now sequenses, tables and strings work as expected 
(pointers though seem to not work, silently; probably just all unsafe features 
are disallowed, like yet casts and FFI).

The idea to begin with then was to create an extendable list of association of 
interfaces to types, implementing them (interface#1 => (type#1, type#2, ...), 
...), then to append items to it in `implements` macro, and in a concept's body 
to check that the type tested is in the list for that concept. 


Re: How check if expression has a type without triggering compilation failure

2017-04-04 Thread LeuGim
> template filter(expr: untyped) =
> 
> 
> when compiles(expr):
> when expr is seq[bool]: echo "bool" elif expr is seq[int]: echo "int" 
> else: echo "something else"
> else:
> echo "can't compile"
> 
> filter(a + b)

It seems code-highliting is broken. 


Re: Base type for all procedure pointers

2017-04-06 Thread LeuGim
Why not to use `pointer` instead of `array[8, byte]`. Will Work for both 64 and 
32 bits.


Re: Disable debug for specific function

2017-09-01 Thread LeuGim
Try pragams like `{.checks: on.}`/`{.checks: off.}` and the like (there are 
ones for specific checks), better via `{.push checks: off.}` and then 
`{.pop.}`, so for the rest of the code checks are still contolled by configs 
and command line. For the 2nd, try `GC_disable`/`GC_enable` (inside the proc).


Re: Exploring namespaces support in Nim

2017-01-25 Thread LeuGim
**@lltp**: I've meant, if `type(A'M*A'M) == type(A)`, then what is 
`type(A:T1'M*B:T2'M)`?


Re: BASS lib

2016-10-13 Thread LeuGim
Don't know whether a bug in the DLL or a wrong usage: the loop in the example 
is executed successfully 65 times and the program fails on the 66'th call of 
`BASS_ChannelIsActive`. The same with different sleep times, so with bigger 
sleep times it plays longer before failure. The same for different files (MP3 
and OGG).

Yet in the example parentheses are missing for `BASS_Free`.


Re: complex statement requires indentation

2018-03-28 Thread LeuGim
Updated.

Yes, can be chained, updated the examples too.

> Also let's mention some keywords

Don't know... "empty coalescing"?.. "double question"? Probably it can be found 
by just 2 words "coalescing operator" when combined with "Nim".


Re: Min: a Nim-based minimalist, concatenative, functional REPL & script lang

2017-08-10 Thread LeuGim
**Note to admin**: that post is a full copy of the first (_Libman_'s) post, 
after the first 2 words.


Re: What are you writing using nim? :)

2017-08-22 Thread LeuGim
Web-crawling/parsing, automation scripts.


Re: Macros and imports

2017-01-01 Thread LeuGim
You don't need anything special for this. Just the usual rules apply for 
cross-module use: if the macro is defined in one module and the procedure 
created by it is used in another, then just mark with `*` (as exported symbol) 
either the macro itself (if it will be called in the second module, so that the 
procedure will be created in that) or the procedure (if the macro will be 
called in the first module, in which it is defined - then you don't need to 
import the macro, instead the proc to which it expanded).

Happy New Year to everyone!


Re: Partial casing is foo_bar

2016-07-20 Thread LeuGim
_OderWat:_ There is nothing wrong with Basic or simplicity, just each language 
has some its characteristic feature, its accent. There cannot be C without 
pointer arithmetic, or Java without OOP, Basic without simplicity, Haskell 
without functional programming stuff, be each of those accents considered as 
good or bad. Of course Nim can go on without case/style-insensitivity, it's not 
such a fundamental feature for it (not like, say, macros or concepts). But 
striving for overall simplicity would mean to get rid of 99% of Nim (macros, 
templates, converters, pragmas, ..., lots of stuff) and to create quite an 
opposite language - then why to begin with Nim.

And C++ can be here as an example. It started as a more powerful (more complex, 
more expressive) kind of C. Now lots of people use C and lots of people use 
C++, each choosing among simplicity and expressiveness, and every of two 
choices has its pros. But could C++ exist now, were it decided to be simple? It 
needed to be somewhat different (especially from C) for its existence to have 
sense.


Re: Why does this not compile, and how can I fix it?

2017-09-23 Thread LeuGim
You can fix it by disambiguating the passed proc name, `isDigit` -> 
`module_name.isDigit` (you see in the error message, that this is the cause). 
Yet you can turn the corresponding parameter into `untyped`.


Re: Defining an array inside a tuple

2017-08-29 Thread LeuGim
Arrays are not special, just having them of length of 100 you won't want to 
initialize them by a literal, the same for seqs.


type GlyphArray* = array[3,  int]
type
  TextBuffer* = tuple
position: tuple[ x : float, y : float ]
cursor  : tuple[ row : int, col : int ]
glyphPositions  : GlyphArray
linePositions   : seq[tuple[ start: int, stop: int]]
text: string

var my_text : TextBuffer = (position: (25.0, 25.0), cursor: (0,0), 
glyphPositions: [3,5,7].GlyphArray, linePositions: @[(0,0)], text:"")
echo my_text.repr



Re: ref object or object with ref field

2017-04-12 Thread LeuGim
> For dynamic dispatch to work on an object it should be a reference type as 
> well.

That is, this will call RootObj's method, not A's and B's (continuing 
**Krux02**'s example):


var values : array[2, RootObj]= [a, b]

for p in values:
  p.foo



Re: Should/can we get explicit concepts?

2017-09-01 Thread LeuGim
I consider this possibility a very useful even without additional checks (those 
in the concept body), like of existence of procedures defined for the type with 
stated signatures and the like, exactly because the programmer explicitly 
declares the purpose of his type and what can be done with, what functionality 
is really supported by the type. I think this explicit promise/contract is the 
main point for interfaces in Delphi, Java, PHP, C#, and signature checking is 
additional to that.

I'll try to make it more visual:


type Browser = concept type b
  proc goTo(self: b, url: string)
  proc back(self: b)
  proc forward(self: b)
proc makeSomeStuffWithABrowser(br: Browser) = 
br.goTo("http://www.nim-lang.org/";)

# creating a concrete type satisfying the concept
type MySimpleBrowser = distinct int # whatever it would be
proc goTo(self: MySimpleBrowser, url: string) = echo "going to " & url & " 
with MySimpleBrowser"
proc back(self: MySimpleBrowser) = discard
proc forward(self: MySimpleBrowser) = discard

# using it
var sb: MySimpleBrowser
makeSomeStuffWithABrowser(sb) # it works, well; it should

# here we don't want to define another Browser, just an unrelated type; 
maybe in another module
type FileManager = distinct int
proc goTo(self: FileManager, path: string) = echo "going to " & path & " 
with X"
proc back(self: FileManager) = discard
proc forward(self: FileManager) = discard

var fm: FileManager
# and here by accident...
makeSomeStuffWithABrowser(fm) # works too :(


Lando's suggestion is perfect in my view, if not to restrict it to object type 
- it can fit equally well any types, as concepts do. It can be seen like a type 
class (like e.g. `SomeReal* = float|float32|float64`), but extendable and with 
inverse binding: created empty and populated with concrete types at their 
definition site. Like:


type X = explicit concept c
  # ...
# X here matches no concrete types, regardless of checks in the concept body
type Y = distinct int satisfies X # conditions in X concept body are 
checked,
  # compile-time error, if not satisfied;
  # Y is added to the list of 
implementations for X
type Z = distinct int satisfies X
proc p(x: X) = discard
# here the same as p(x: Y|Z)


Regarding wording, `explicit concept` and `satisfies` seem to be not worse than 
usual `interface` and `implements`, especially taking into account 
distinctions; just for people coming from those languages those terms may be 
more familiar; maybe `explicit concept` will be easier to understand to others.

Regarding implementation, macro vs. built-in: I wanted to implement such a 
thing some (long) time ago via macros and concepts and was faced then with some 
VM limitations; maybe they were eliminated from then. The intended syntax was 
(for simplicity):


type X = ...
implements X, I



Re: Access procedure arguments from a macro when the procedure is called

2016-11-08 Thread LeuGim
> it's more readable than using `setterProc.params[2][0]`

You don't have to use `setterProc.params[2][0]` with your first approach (with 
`quote do`). Just `value` works - identifier will be resolved in the procedure 
being transformed, not in macro. Oppositely, to use the macro's symbol, you 
have to quote it with backticks. So what you had to change in your first 
example is to add backticks around `limit` (like in _Krux02_'s example), using 
`value` as is (just with `.len` appended).


Re: Error: invalid indentation

2017-09-25 Thread LeuGim
Yes, `object` is a value, `ptr object` is a non-garbage-collected pointer to an 
object, `ref object` is a garbage-collected pointer to an object, `object of 
...` is the way to inherit, to be combined with any of the previous, and after 
any of that a list of fields may go.

`RootObj` is not smth special and built-in, it's defined in `system.nim` (like 
many other things, read that module for better understanding) as `type RootObj* 
{.inheritable.} = object`, a predefined root for inheritance hierarhies, but 
you can create separate hierarchies (your own roots) the same way, marking your 
object type as `{.inheriatable.}`.

`Class3 = ref Class1` \- values of this type will be double references: 
references to referenced (`Class1`) subtype of empty objects (`RootObj`).


Re: Mutability of loop variables

2017-01-12 Thread LeuGim
Gives "redifinition of 'line'" error...


Re: passing references

2016-12-06 Thread LeuGim
Why not just 


echo "IS IT THE SAME? ", xobjref == result


?

They are already addresses both.  



Re: + won't take two different types

2017-07-29 Thread LeuGim
The way to go:


type Addable = concept x, y
  x + y
proc addit(a, b: Addable): auto =
return a + b
echo addit(12, 22.1) # -> 34.1
echo addit({1,3,5},{5,7}) # -> {1,3,5,7}


* * *

Yet you can explicitly convert arguments, this way you decide by yourself what 
type is the result:


proc additF[T, U] (a: T, b: U): auto =
return a.float + b.float
proc additI[T, U] (a: T, b: U): auto =
return a.int + b.int

echo additF(12, 22.1) # -> 34.1
echo additI(12, 22.1) # -> 34


* * *

Yet you can use implicit conversion:


proc addit[T, U] (a: T, b: U): auto =
return a + b
converter x(x: int): float = x.float
echo addit(12, 22.1) # -> 34.1


But it can make the code's logic more messy.

* * *

Below "submit" button there's a hint on making your code sample 
syntax-highlighted, makes reading easier.


Re: Type inference side effects

2016-12-29 Thread LeuGim
No, more implicit code of coarse is more compact (less letters to type and 
read), and this is exactly the reason for type inference to exist.


Re: Winim - Nim's Windows API and COM Library

2017-01-17 Thread LeuGim
WSH scripts in VBScript and in Nim are looking so alike, and so easy to 
translate!

Thanks a lot!


Re: Code substitution with templates

2017-09-26 Thread LeuGim
Your syntax for macro's call is OK, your key-value pair is parsed as a call 
(`id` being regarded as a proc name, and `int` as statement list (block), 
passed to it). Now you need to write a macro, that can use it. In that macro 
you first assign to `result` the constant part of your type, and then add to it 
new nodes, via procs from `macros` module (search forum for examples).


import macros
template obj(tName: untyped): untyped =
  type
tName = object
  fname: string
  age: int
macro typeGen(tName, extraCode: untyped): untyped =
  result = getAst(obj(tName))
  echo result.treeRepr # so you can see, where and how you add fields
  echo extraCode.treeRepr # so you can see, from where and you get them
  # and here you parse ``extraCode`` and add additional nodes to 
result[0][0][2][2];
  # as is now, it will create a type with just 2 fields in the template

typeGen(Employee):
  id: int



Re: Alternative to ugly generic class methods?

2016-11-06 Thread LeuGim
An alternative syntax for the procedures' signatures in the example, maybe is 
more to your taste:


proc insert(this: var Dictionary, key: Dictionary.Key, value: 
Dictionary.Value) =
  ...
proc find(this: var Dictionary, key: Dictionary.Key): Dictionary.Value =
  ...



Re: generic template

2017-10-09 Thread LeuGim
template constructFoo*(T1, T2): untyped = implConstructFoo(T1, T2)


Re: Cannot get name of type using typedesc

2017-10-24 Thread LeuGim
To the developer of "Run", in case if more browser support is needed:

  * "Access-Control-Allow-Origin" header is missing. It's needed for 
cross-domain requests for some 
[browsers](https://developer.mozilla.org/ru/docs/Web/HTTP/Headers/Access-Control-Allow-Origin)
 and by 
[standards](https://fetch.spec.whatwg.org/#http-access-control-allow-origin) 
("play.nim-lang.org" is regarded as a different domain). Firefox logs this: 
Cross-Origin Request Blocked: The Same Origin Policy disallows reading the 
remote resource at https://play.nim-lang.org/compile. (Reason: CORS header 
'Access-Control-Allow-Origin' missing). It can be solved by adding 
response-header `Access-Control-Allow-Origin: https://forum.nim-lang.org` or 
`Access-Control-Allow-Origin: *`.
  * `code` parameter is not sent in requests, only `compilationTarget`, because 
`code`'s content is retrieved via `innerText`, which was not in standards until 
last year and is supported by Firefox only from that time. `innerHTML` is long 
supported and can be used instead, tags then should removed.




Re: Estimation of π using Leibniz series

2017-08-14 Thread LeuGim
At least so: `res += float([1,-1][n mod 2])/(2.0*float(n)+1.0)`.


Re: Exploring namespaces support in Nim

2017-01-20 Thread LeuGim
> from Module import type Foo

Then maybe more explicit, something like:


# module A

type
  Person* = object
user*: string
age*: int

proc `$`*(p: Person): string = p.user

export (Person, `$`*(p: Person): string) as C



# module B

from A import C
var x = Person(user: "Gustav Gans", age: 45)
# $ for Person is called
echo x


Should be less work for the compiler, and any set of symbols can be combined, 
not just one type; so a module can be logically subdivided in any possibly 
overlapping parts, not affecting its inner structure anyhow.


Re: Nim VFS (virtual file system)

2017-01-16 Thread LeuGim
The idea ha nothing to do with decreasing download time or size, just easing 
dealing with sources, like treating the archive file as a directory, not having 
to unpack it first.


Re: complex statement requires indentation

2018-03-27 Thread LeuGim
Didn't think about laziness, indeed, it should. 


template `??`[T](val, alternative: T): T =
  const zero = zeroval[T]()
  if val==zero:
alternative
  else:
when compiles(val.len):
  if val.len==0: alternative
  else: val
else: val


* * *

No, I don't know about talks. Youtube?


Re: Cannot get name of type using typedesc

2017-10-23 Thread LeuGim
"Run" button doesn't work for me, does nothing. JS enabled.


Re: Nim VFS (virtual file system)

2017-01-11 Thread LeuGim
This would be extremely cool!

There was [some discussion](http://forum.nim-lang.org/t/937) on the forum about 
multiple modules per file, which could give some of the same advantages. And 
source-files archives treated as folders exist yet for Java and PHP (.jar and 
.phar).


Re: New high level ODBC library for SQL Server

2017-10-02 Thread LeuGim
@michael, are those indentations before `con.something` needed? If those are 
just value assignments to fields of an object, you should do that outside of a 
variable definition block.


Re: Thoughts on imports

2017-07-23 Thread LeuGim
> Writing `from blah import nil` for every import is ugly

Probably less idiomatic/encouraged way should not be absolutely the same easy, 
as more idiomatic. So two extra words for the whole imports list should be OK, 
it could be like this: `from xxx, yyy import nil`.


Re: Concept[T] design question

2016-08-23 Thread LeuGim
Maybe I didn't get the point about `Copyable and Comparable`: this is an 
existing syntax for years and it works well AFAIK.


Re: Traybar support ?

2017-10-02 Thread LeuGim
That's simple enough, considering that's a C API, and not an genuine Nim's 
library. C doesn't have Nim strings, so you copyMem your string to its 
char-array; not such a problem. You can find all constants needed in 
`MinGW/include`, just make a text-search over the folder (matter of seconds); 
they are taken initially from there to `windows` module, and you can of coarse 
update it.

Explanations of API functions and constants are in WinAPI Help, you probably 
have that with your programming tools; the docs are surprisingly good and 
easy-explorable, mostly you won't even need to search the web (though that is 
there too). I have it in hlp-format, there you enter in **index** 
`CreatePopupMenu`, and get the spec for the function you need, links to related 
functions (`InsertMenuItem`, ...) and **overview** button for the general 
information; a search and hierarchial contents are also there; that's really 
well-organized, not some mess of texts.

But certainly that won't be a single line to write, so was the advise to search 
first in existing Nim libraries.


Re: Partial casing is foo_bar

2016-07-19 Thread LeuGim
> Simplify, simplify, simplify

Such a language already exists, Basic. But instead of just using that probably 
it's more fun to choose one of the most feature-rich languages and advertise 
triple simplicity for it. Then further steps: promote rejecting pointer 
arithmetic in C and OOP in Java.


Re: My stupid usage of cstrings

2017-01-23 Thread LeuGim
Yes, if the strings used are stored somewhere as `string` at the time they are 
checked, the output is normal, e.g.:


var s: seq[string]
proc genArray(i, j: int) : seq[cstring] =
  result = newSeqOfCap[cstring](j - i + 1)
  s = newSeqOfCap[string](j - i + 1)
  for k in i .. j:
s.add $k
result.add((s[k-i]).cstring)



Re: Advent of Nim

2017-10-05 Thread LeuGim
Probably it was on moderation. Now it's visible.


Re:

2017-08-29 Thread LeuGim
  * yes, to make inheritance easier (vars of different types (ancestors, 
descendants) are of the same size, size of a pointer)
  * no copying when passing - good for large objects, or when transmitted or 
used as arguments often
  * you can use arrays/seqs of different-sized (disregarding inheritance) 
ref-objects - really arrays of pointers
  * you can even store them in collections of arbitrary references (of any, 
incl. non-object, type) or just pointer-sized values



And the like, just examples.

Ref-objects are allocated on heap, that is they require memory allocation, so 
when you don't have reasons to use them (in simple cases esp.), better to use 
value objects, which in Nim are no-overhead (say, a no-inheritance object 
containing 2 integers is of the size 2 integers, which are located directly in 
it and are passed to procs on stack).


Re: Error with using concepts

2017-07-12 Thread LeuGim
Just define `log(varargs[F])` before `log(Fer)`. From the error messages you 
see in the body of `log(Fer)` only this one `log` is known, compiler is unaware 
of the second.


Re: trying to find a language very like nim

2016-08-08 Thread LeuGim
Interesting, it has `slurp` with the same meaning, as in Nim.


Re: Big integer litterals

2018-03-03 Thread LeuGim
_Stefan_Salewski:_ Your example though compiles, gives wrong result - just of 4 
lower bytes. 


 var x: int = 10 * 1_000_000_000
var y: int = 1410065408
echo x   # => 1410065408
echo x == y  # => true
echo x == (10_000_000_000 and 0x_)  # => true


This should be because of Nim's/C's compiler's 32-bitness.


Re: Estimation of π using Leibniz series

2017-08-14 Thread LeuGim
Using exponentiation just for interlacing 1, -1, 1, -1, ... is pointless (apart 
from mathematical formulas on paper) and should not be done, so no matter if 
some compiler optimizes it.


Re: Nim and hot loading - any experiences to share?

2017-09-24 Thread LeuGim
I get that SIGSEGV instantly, _exit via ctrl + c_ and 1 _version 1_ been 
printed. I get that immediate SIGSEGV even for empty _main.nim_ and _lib.nim_.


Re: Question about using the "new" built in

2016-12-21 Thread LeuGim
[http://nim-lang.org/docs/manual.html#types-object-construction](http://forum.nim-lang.org///nim-lang.org/docs/manual.html#types-object-construction)

"For a `ref object` type `system.new` is invoked implicitly."


Re: Are array types that differ only in index boundaries different?

2017-09-26 Thread LeuGim
Regarding assignment, it doesn't have to depend on types being 
indistinguishable. E.g.:


proc p(x: int) = echo "int"
proc p(x: int8) = echo "int8"
var x: int8
x=3 # implicit conversion
p x # int8
p 3 # int


overloading works here, while allowing literal's assignment with implicit 
conversion.


Re: `-` operator overloading and negative numbers of distinct type

2016-07-13 Thread LeuGim
The overflow is because of an infinite loop (and compiler shows it). Your proc 
`-` does nothing, except of calling itself with same argument. It doesn't call 
the `-` of `float32`, as you probably expect - the arguments type is still 
`F_TYPE`. So just say to compiler to call the `-` of `float32`, by calling it 
for an `F_TYPE` value:


proc `-`*(a:F_TYPE): F_TYPE =
  return (-a.float32).F_TYPE


The same for two other procs.

Or you can do simpler - just borrow parent type's procs:


proc `-`*(a:F_TYPE): F_TYPE {.borrow.}



Re: What happened to term rewriting macro?

2017-07-29 Thread LeuGim
I hope there's no plans of deprecation/removal, docs are where there were, 
docs/manual/trmacros.txt.


Re: Enum related error: duplicate case value

2016-06-29 Thread LeuGim
There's a pragma for setting the size of an enum. Works with 
`SUBSCRIPTIONS_REQUEST = 0x` if the enum is defined beginning with 
`EVENT_GROUPS* {.size: sizeof(cint).} = enum ``, and ``var v:EVENT_GROUPS = 
HANDLE_INITIALIZATION` is uncommented instead of `var v = 0`.


Re: Formatted Backend Output?

2017-10-08 Thread LeuGim
nim c --lineDir:on --embedsrc yourProjectFile


Re: My stupid usage of cstrings

2017-01-23 Thread LeuGim
or


proc genArray(i, j: int) : seq[cstring] =
  result = newSeqOfCap[cstring](j - i + 1)
  for k in i .. j:
let s = $k
GC_ref(s)
result.add(s.cstring)



Re: Macros and imports

2017-01-02 Thread LeuGim
There should be nothing special for this case, if the macro is used in the same 
module, where defined. You just need to use `import` before calling the macro 
(but can use after the macro definition itself).

If the proc is defined in one module (_a_), the macro in another (_b_) and is 
called in yet another (_c_), then you need either:

  * `import a` in _c_, prior to calling the macro; no need then to import _a_ 
in _b_, the macro will use an unbound identifier; so you can really then have 
in the same program some another module (_a2_) defining a proc with same name 
and imported, together with _b_, in yet another module (_c2_); so, in _c_ a 
proc from _a_ will be called, and in _c2_ \- from _a2_, both via the same macro 
from _b_.
  * you can bind the identifier used in macro (for the proc) to the actual 
symbol (to the proc from _a_), using `newCall(bindSym"theProcFromA")` instead 
of `newCall("theProcFromA")` (what Araq suggested), so what imported in _c_ (or 
where the macro is used) doesn't matter; _a_ should be imported in _b_ then 
before the macro's definition.
  * in templates or quote do: in macros by default identifier is bound if the 
symbol is in scope of the macro definition (i.e. will refer to the same proc), 
and unbound otherwise; you can force binding (as with `bindSym`) by using 
`bind` statement (then you'll get a compile-time error, if the proc is not in 
the scope, instead of late binding), or force letting it unbound by `mixin` 
statement; in `quote do:` you can also just use backticks around identifiers 
for explicit binding (you might need to declare the proc with as _procvar_ 
(say, via `{.procvar.}`) for this to work).



E.g.: 


# module a
proc p* = echo "p of a"
proc pv* {.procvar.} = echo "pv of a"

#module a2

proc p* = echo "p of a2"

# module b
import a
import macros

macro x1*: untyped =
  result = newNimNode(nnkStmtList)
  result.add newCall(bindSym"p")

# the same
macro x2*: untyped =
  result = quote do:
bind p
p()

# yet the same, but ``pv`` should be a ``procvar``
macro x3*: untyped =
  result = quote do:
`pv`()

# all ``x1``, ``x2`` and ``x3`` will call ``a.p``/``a.pv``, wherever called

# ``p`` is always unbound
macro y1*: untyped =
  result = newNimNode(nnkStmtList)
  result.add newCall("p")

# ``p`` is bound, just because *a* is imported, would be unbound otherwise
macro y2*: untyped =
  result = quote do:
p()

# ``p`` is implicitly unbound
template y3* =
  mixin p
  p()



# module c
# the main module for the example
import b
x1() # -> p of a
x2() # -> p of a
x3() # -> p of a
import a
y1() # -> p of a
y2() # -> p of a
y3() # -> p of a
import c2


# module c2
import b
x1() # -> p of a
x2() # -> p of a
x3() # -> pv of a
import a2
y1() # -> p of a2
y2() # -> p of a
#y3() # won't compile, both ``p`` from *a* and *a2* match





Re: Traybar support ?

2017-10-01 Thread LeuGim
If it's for windows, the API itself is quite simple (maybe it's not hard for 
other platforms too). There are several gui frameworks available, there may be 
this functionality available, better check them first.

A quick example for WInAPI (`nimble install oldwinapi` to make `windows` 
available): 


import windows, os
# some missing stuff
const NIF_ICON  = 0x0002
const NIF_TIP   = 0x0004
const NIF_STATE = 0x0008
const NIM_ADD   = 0.DWORD
const NIM_MODIFY= 1.DWORD
const NIM_DELETE= 2.DWORD

# a dummy window, to pass its handle to tray icon's creation proc;
# use any your program's window instead, and then just skip this piece of 
code
let className = "BUTTON"
let windowName = "test"
let hw=CreateWindow(
  className.cstring,
  windowName.cstring,
  0, # dwStyle
  400, 300, 200, 60, # position and size
  0, # hWndParent
  0, # hMenu
  0, #hInstance
  nil)

# just filling the structure, describing your icon, and passing it to the 
API proc;
# a callback can be set here too
var nid: NotifyIconDataA
nid.cbSize = nid.sizeof.DWORD
nid.Wnd = hw
nid.uFlags = NIF_ICON or NIF_TIP
nid.hIcon = LoadIcon(0, IDI_EXCLAMATION)
var s = "Hello from WinAPI!"
copyMem nid.szTip.addr, s[0].addr, s.len
nid.szTip[s.len] = '\0'
discard Shell_NotifyIconA(NIM_ADD, addr nid)

# here should be your message loop; you have that propbably already;
# instead, for a demostration, we just keep the process alive for some 
seconds,
# enough to see icon working, with a hint on it
sleep 8_000



Re: Community name?

2018-03-02 Thread LeuGim
Because C programmers don't constitute a community (probably did in 1970s), and 
mostly don't even choose, just happen to program in C, and new languages have 
not just users, but rather followers, they have to be a bit of a cult to have 
ones. Well, it is so not only about languages.


Re: Using this over tables?

2017-10-09 Thread LeuGim
Of coarse you can use it. But yes, performance will suffer, if you have more 
than several items in such a table (you iterate through half its length on 
average).

The syntax is described in the manual, and is the usual way to set initial 
values for hash-tables.


  1   2   3   >