www.digitalmars.com         C & C++   DMDScript  

digitalmars.D.learn - in / out for C++ programmers

reply "Dan " <enjoysmath gmail.com> writes:
When would you use in / out parameters instead of ref & const 
keywords?

Thanks.
Mar 23 2012
next sibling parent Jonathan M Davis <jmdavisProg gmx.com> writes:
On Saturday, March 24, 2012 07:28:08 Dan wrote:
 When would you use in / out parameters instead of ref & const
 keywords?
out sets the variable to its init value, so you don't run into issues with the behavior of the function changing based on the value of the variable that you passed in. out is intended for variables that are for returning an extra value from the function, not passing one in. You use ref if you want to actually use the value that you pass in. in is the same as const scope and has nothing to do with ref at all. - Jonathan M Davis
Mar 23 2012
prev sibling parent reply =?UTF-8?B?QWxpIMOHZWhyZWxp?= <acehreli yahoo.com> writes:
On 03/23/2012 11:28 PM, Dan wrote:
 When would you use in / out parameters instead of ref & const keywords?
I am just about finished translating a chapter exactly on that topic. I've just realized that I have some questions myself. :) 'out' is the equivalent of a reference in C++, with additionally initializing the out parameter upon entry to the function. void foo(out int i) { assert(i == 0); // regardless of what it was before the call } 'in' is the same as 'const scope'. const part is easy to understand but I don't know what 'scope' does. I could not understand what the spec means with "references in the parameter cannot be escaped (e.g. assigned to a global variable)" for scope: http://dlang.org/function.html 'ref' is the same as a C++ reference. Ali
Mar 23 2012
parent reply Jonathan M Davis <jmdavisProg gmx.com> writes:
On Friday, March 23, 2012 23:37:27 Ali =C3=87ehreli wrote:
 'in' is the same as 'const scope'. const part is easy to understand b=
ut
 I don't know what 'scope' does. I could not understand what the spec
 means with "references in the parameter cannot be escaped (e.g. assig=
ned
 to a global variable)" for scope:
=20
    http://dlang.org/function.html
You mean that you don't understand what it means for a reference to esc= ape a=20 function? One example of this with pointers would be int* func() { int a; return &a; } A pointer to a local variable has escaped the function. That pointer is= =20 invalid. A case this simple gets caught by the compiler, but it's very = easy=20 to get around that (e.g. passing &a to a function which returns it and = then=20 return the result of that function rather than &a directly). In the case of scope, it means that what you pass in cannot be assigned= to a=20 global or static variable, and it cannot be returned from that function= . So,=20 for instance. int[] foo(const int[] a) { ... } could not assign a to a global or static variable and cannot return it.= This=20 can allow some additional optimizations as well as improve safety in so= me=20 cases. For instance, if you pass int[5] b; to foo, then you know that no slice of that static array will escape, s= ince=20 something like int[] bar() { int[5] c; return c; } is just as bad as the case with &a. I believe that scope is used primar= ily=20 with delegates however (particularly, since you often _want_ to be able= to=20 return a slice of an array passed to a function). It guarantees that th= e the=20 delegate's context won't escape the function and can make it so that th= e=20 delegate's context doesn't have to be allocated on the heap, which impr= oves=20 efficiency. scope is pointless with types which aren't pointers or references thoug= h. - Jonathan M Davis
Mar 23 2012
next sibling parent reply =?UTF-8?B?QWxpIMOHZWhyZWxp?= <acehreli yahoo.com> writes:
On 03/23/2012 11:50 PM, Jonathan M Davis wrote:
 On Friday, March 23, 2012 23:37:27 Ali Çehreli wrote:
 'in' is the same as 'const scope'. const part is easy to understand but
 I don't know what 'scope' does. I could not understand what the spec
 means with "references in the parameter cannot be escaped (e.g. assigned
 to a global variable)" for scope:

     http://dlang.org/function.html
You mean that you don't understand what it means for a reference to
escape a
 function?
No. I've known that for decades now. I don't understand it because I've tried what I've understood about scope in code examples and could not see any difference. Also, I don't understand the semantics of it. For example, 'const' is welcoming: it says "I accept mutable and immutable references as parameters." (Because it is a guarantee that it will not modify.) 'immutable' is restricting: "I accept only immutable references." What is 'scope' on a parameter? Is that a guarantee or a requirement on the argument?
 In the case of scope, it means that what you pass in cannot be 
assigned to a
 global or static variable, and it cannot be returned from that 
function. So,
 for instance.

 int[] foo(const int[] a)
 {
      ...
 }

 could not assign a to a global or static variable and cannot return it.
Yet this compiles: int[] g; int[] foo(scope int[] slice) { g = slice; return slice; } void main() { int[] slice; int[] result = foo(slice); } The funny thing is, what does function have to do the scope of a parameter that is passed to it? Since it's an argument passed from the outside it may be scoped or dynamic. And that's why I don't understand it. :) I suspect scope is a remnant from the D1 days. (?)
 This
 can allow some additional optimizations as well as improve safety in some
 cases. For instance, if you pass

 int[5] b;

 to foo, then you know that no slice of that static array will escape, 
since
 something like

 int[] bar()
 {
      int[5] c;
      return c;
 }

 is just as bad as the case with&a. I believe that scope is used primarily
 with delegates however (particularly, since you often _want_ to be 
able to
 return a slice of an array passed to a function).
Fine, delegates... Is that a guarantee or a requirement in that context?
 It guarantees that the the
 delegate's context won't escape the function and can make it so that the
 delegate's context doesn't have to be allocated on the heap, which 
improves
 efficiency.

 scope is pointless with types which aren't pointers or references though.

 - Jonathan M Davis
Ali
Mar 24 2012
next sibling parent Jonathan M Davis <jmdavisProg gmx.com> writes:
On Saturday, March 24, 2012 00:02:58 Ali =C3=87ehreli wrote:
 On 03/23/2012 11:50 PM, Jonathan M Davis wrote:
  > On Friday, March 23, 2012 23:37:27 Ali =C3=87ehreli wrote:
  >> 'in' is the same as 'const scope'. const part is easy to understa=
nd
  >> but
  >> I don't know what 'scope' does. I could not understand what the s=
pec
  >> means with "references in the parameter cannot be escaped (e.g.
  >> assigned
  >>=20
  >> to a global variable)" for scope:
  >>     http://dlang.org/function.html
  >=20
  > You mean that you don't understand what it means for a reference t=
o
=20
 escape a
=20
  > function?
=20
 No. I've known that for decades now. I don't understand it because I'=
ve
 tried what I've understood about scope in code examples and could not=
 see any difference.
=20
 Also, I don't understand the semantics of it. For example, 'const' is=
 welcoming: it says "I accept mutable and immutable references as
 parameters." (Because it is a guarantee that it will not modify.)
 'immutable' is restricting: "I accept only immutable references."
=20
 What is 'scope' on a parameter? Is that a guarantee or a requirement =
on
 the argument?
=20
  > In the case of scope, it means that what you pass in cannot be
=20
 assigned to a
=20
  > global or static variable, and it cannot be returned from that
=20
 function. So,
=20
  > for instance.
  >=20
  > int[] foo(const int[] a)
  > {
  >=20
  >      ...
  >=20
  > }
  >=20
  > could not assign a to a global or static variable and cannot retur=
n it.
=20
 Yet this compiles:
=20
 int[] g;
=20
 int[] foo(scope int[] slice)
 {
      g =3D slice;
      return slice;
 }
=20
 void main()
 {
      int[] slice;
      int[] result =3D foo(slice);
 }
=20
 The funny thing is, what does function have to do the scope of a
 parameter that is passed to it? Since it's an argument passed from th=
e
 outside it may be scoped or dynamic.
=20
 And that's why I don't understand it. :) I suspect scope is a remnant=
 from the D1 days. (?)
The point of scope is to guarantee that no references to the argument p= assed=20 in can escape the function. The variable passed in is irrelevant aside = from=20 whether it's a reference type (or pointer) or not. Now, there's every=20= possibility (guarantee even, given your example) that scope is buggy. B= ut as=20 I understand it (and the spec seems to agree), the whole point of scope= is=20 to make it illegal for any argument passed to that parameter to escape = the=20 function it's being passed to. So, it restricts what the callee can do,= but=20 it doesn't restrict the caller.
  > This
  > can allow some additional optimizations as well as improve safety =
in
  > some
  > cases. For instance, if you pass
  >=20
  > int[5] b;
  >=20
  > to foo, then you know that no slice of that static array will esca=
pe,
=20
 since
=20
  > something like
  >=20
  > int[] bar()
  > {
  >=20
  >      int[5] c;
  >      return c;
  >=20
  > }
  >=20
  > is just as bad as the case with&a. I believe that scope is used
  > primarily
  > with delegates however (particularly, since you often _want_ to be=
=20
 able to
=20
  > return a slice of an array passed to a function).
=20
 Fine, delegates... Is that a guarantee or a requirement in that conte=
xt? If the parameter that a delaget is being passed to is marked as scope, = then=20 it's supposed to be illegal for any references to it or its context to=20= escape the function it's being passed to, which makes it possible for t= he=20 compiler to avoid putting the delegate's context on the heap. That is a= =20 guarantee, and if it's not true, then the compiler is buggy. What I don= 't=20 know is if the language guarantees that the compiler will do the=20 optimization of not putting the delegate's context on the heap if it's=20= passed to a scope parameter. - Jonathan M Davis
Mar 24 2012
prev sibling parent reply Jonathan M Davis <jmdavisProg gmx.com> writes:
Apparently, scope parameters aren't currently checked at all, so they're 
_very_ buggy:

http://d.puremagic.com/issues/show_bug.cgi?id=6931

- Jonathan M Davis
Mar 24 2012
parent =?UTF-8?B?QWxpIMOHZWhyZWxp?= <acehreli yahoo.com> writes:
On 03/24/2012 12:18 AM, Jonathan M Davis wrote:
 Apparently, scope parameters aren't currently checked at all, so they're
 _very_ buggy:

 http://d.puremagic.com/issues/show_bug.cgi?id=6931

 - Jonathan M Davis
Thank you. I take it that 'scope' is a way of a function to promise that it will not hold on to that reference longer than the function call. In this sense, 'scope' means "the caller may pass in variables of *even* scope duration." That makes sense to me. :) Ali
Mar 24 2012
prev sibling parent =?UTF-8?B?QWxpIMOHZWhyZWxp?= <acehreli yahoo.com> writes:
On 03/23/2012 11:50 PM, Jonathan M Davis wrote:
 I believe that scope is used primarily
 with delegates however (particularly, since you often _want_ to be 
able to
 return a slice of an array passed to a function). It guarantees that 
the the
 delegate's context won't escape the function and can make it so that the
 delegate's context doesn't have to be allocated on the heap, which 
improves
 efficiency.
Ok, I read it more carefully. What you are saying is that 'scope' may make more sense when applied to a parameter of a delegate. There are two parties involved: - User of the delegate as in dlg(someArg); - Creater of the delegate as in 'return a => a + localVariable;' Is that a requirement of the delegate or the user of the delegate in that case? Or, is that a guarantee of the delegate or the caller of the delegate? Yes, I am completely lost on the semantics of 'scope' parameters. :) Ali
Mar 24 2012