By using this site, you agree to our updated Privacy Policy and our Terms of Use. Manage your Cookies Settings.
425,534 Members | 1,830 Online
Bytes IT Community
+ Ask a Question
Need help? Post your question and get tips & solutions from a community of 425,534 IT Pros & Developers. It's quick & easy.

how to pass by const reference?

P: n/a
Why does VB.NET V2 force me to pass by value for my set function? When I try
to change it to const byref it gives me a syntax error. It seems very
inefficient to be passing strings around by value when a reference to a
constant string object will do fine (all we are going to do is copy it). In
my case, would the byval for the set function cause a superfluous copy?
Thanks,
Siegfried

class person
dim m_name as string
public sub new (n as string)
m_name = n
end sub
public property name () as string
Get
return m_name
end get
set ( const byref value as string)
m_name = value
end set
end Property
public overloads overrides function ToString() as string
return m_name
end function
protected overloads overrides sub Finalize()
outp.WriteLine("~" & name )
MyBase.Finalize()
end sub
End Class
Jan 16 '08 #1
Share this Question
Share on Google+
14 Replies


P: n/a
"Siegfried Heintze" <si*******@heintze.comwrote in message
news:OH****************@TK2MSFTNGP06.phx.gbl...
Why does VB.NET V2 force me to pass by value for my set function? When I
try to change it to const byref it gives me a syntax error. It seems very
inefficient to be passing strings around by value when a reference to a
constant string object will do fine (all we are going to do is copy it).
In my case, would the byval for the set function cause a superfluous copy?
It doesn't create a second copy of the string, just the pointer to it. So
you have 2 pointers pointing to the 1 string. If you change the string from
1 pointer it will create a copy then I believe.

Michael
Jan 16 '08 #2

P: n/a
Why does VB.NET V2 force me to pass by value for my set function?
set ( const byref value as string)
I have never heard of the const keyword being used here.

Try skipping it.

--
Rory
Jan 16 '08 #3

P: n/a

"Michael C" <mi**@nospam.comwrote in message
news:u2*************@TK2MSFTNGP04.phx.gbl...
"Siegfried Heintze" <si*******@heintze.comwrote in message
news:OH****************@TK2MSFTNGP06.phx.gbl...
>Why does VB.NET V2 force me to pass by value for my set function? When I
try to change it to const byref it gives me a syntax error. It seems very
inefficient to be passing strings around by value when a reference to a
constant string object will do fine (all we are going to do is copy it).
In my case, would the byval for the set function cause a superfluous
copy?

It doesn't create a second copy of the string, just the pointer to it. So
you have 2 pointers pointing to the 1 string. If you change the string
from 1 pointer it will create a copy then I believe.
That is correct. By default all arguments in VB .NET are passes ByVal and
passing an argument ByVal means you get a copy - - but not necessarially a
copy of the data. If you pass a reference type (which a String is) ByVal,
you get a copy of the pointer to the reference type, thus having two ways to
access the one memory address. If you pass a value type (like an Integer)
ByValue, then you get a copy of the actual data stored on the stack.

If you were to pass a reference type (String) ByRef, then you'd get a
pointer to the original pointer, which points to the memory. A pointer to a
pointer is not as effiicient as a copy of the first pointer.
>
Michael

Jan 16 '08 #4

P: n/a
You can't do this.

Const is used to declare a constant and when declaring a constant, you must
assign it a value. Const can't be used to force an argument to become
constant.

-Scott

"Rory Becker" <Ro********@newsgroup.nospamwrote in message
news:b5**************************@msnews.microsoft .com...
>Why does VB.NET V2 force me to pass by value for my set function?
>set ( const byref value as string)

I have never heard of the const keyword being used here.

Try skipping it.

--
Rory


Jan 16 '08 #5

P: n/a
My understanding is that in .NET, all strings with the same contents will be
the same instance anyway.

So for example try the following code
Dim strA As String = "ABCDEF"
Dim strB As String = "ABCDEF"
MsgBox(String.ReferenceEquals(a, b))

It returns "True"!

Strings are now reference types, so whether you pass ByRef or ByVal, you are
passing (or copying) a pointer, not the contents of the string itself.

I think the reason is as old as the hills. Strings in BASIC have always been
variable length, and Microsoft has always tried to hide Pointers, memory
addresses etc from BASIC programmers. Being variable length, you need either
a terminator or a length field in memory so the computer knows where the end
of the string is. But in the BASIC paradigm, the "whole variable" only
consists of the characters, so the language must hide the terminator/length
field. The way VB does this is by making strings Reference types, then making
strings immutable and non-repeating. So if you do the comparison
If strA = strB Then ...
technically you are comparing REFERENCES (ie. that they point to the same
part of memory) rather than comparing the contents of the variables.
--
David Streeter
Synchrotech Software
Sydney Australia
"Siegfried Heintze" wrote:
Why does VB.NET V2 force me to pass by value for my set function? When I try
to change it to const byref it gives me a syntax error. It seems very
inefficient to be passing strings around by value when a reference to a
constant string object will do fine (all we are going to do is copy it). In
my case, would the byval for the set function cause a superfluous copy?
Thanks,
Siegfried

class person
dim m_name as string
public sub new (n as string)
m_name = n
end sub
public property name () as string
Get
return m_name
end get
set ( const byref value as string)
m_name = value
end set
end Property
public overloads overrides function ToString() as string
return m_name
end function
protected overloads overrides sub Finalize()
outp.WriteLine("~" & name )
MyBase.Finalize()
end sub
End Class
Jan 16 '08 #6

P: n/a
Addendum: In some ways, it is quite elegant, since comparisons will take the
same amount of time irrespective of the size of the strings being compared
(i.e. there is no character-by-character comparison). Also, additional copies
of the string take up an insignificant amount of memory.

Downside is that code like:
for i as integer = 0 to 100: strA &= "A": Next i
would be much slower, since you are creating a new string at each iteration
rather than extending an existing one. (I think there is a StringBuilder
class which is designed for this sort of work).

One major change from VB6 is that Strings are no longer collections of
Bytes, but collections of Characters. In other words, Strings are no longer a
good choice for storing binary data. Byte arrays are fairly good, but I get
sick of type CByte whenever I want to use a particular byte value as an
operand. Oh for a type character for byte!!

At least they got rid of BSTRs!!


--
David Streeter
Synchrotech Software
Sydney Australia
"SurturZ" wrote:
My understanding is that in .NET, all strings with the same contents will be
the same instance anyway.

So for example try the following code
Dim strA As String = "ABCDEF"
Dim strB As String = "ABCDEF"
MsgBox(String.ReferenceEquals(a, b))

It returns "True"!

Strings are now reference types, so whether you pass ByRef or ByVal, you are
passing (or copying) a pointer, not the contents of the string itself.

I think the reason is as old as the hills. Strings in BASIC have always been
variable length, and Microsoft has always tried to hide Pointers, memory
addresses etc from BASIC programmers. Being variable length, you need either
a terminator or a length field in memory so the computer knows where the end
of the string is. But in the BASIC paradigm, the "whole variable" only
consists of the characters, so the language must hide the terminator/length
field. The way VB does this is by making strings Reference types, then making
strings immutable and non-repeating. So if you do the comparison
If strA = strB Then ...
technically you are comparing REFERENCES (ie. that they point to the same
part of memory) rather than comparing the contents of the variables.
--
David Streeter
Synchrotech Software
Sydney Australia
"Siegfried Heintze" wrote:
Why does VB.NET V2 force me to pass by value for my set function? When I try
to change it to const byref it gives me a syntax error. It seems very
inefficient to be passing strings around by value when a reference to a
constant string object will do fine (all we are going to do is copy it). In
my case, would the byval for the set function cause a superfluous copy?
Thanks,
Siegfried

class person
dim m_name as string
public sub new (n as string)
m_name = n
end sub
public property name () as string
Get
return m_name
end get
set ( const byref value as string)
m_name = value
end set
end Property
public overloads overrides function ToString() as string
return m_name
end function
protected overloads overrides sub Finalize()
outp.WriteLine("~" & name )
MyBase.Finalize()
end sub
End Class

Jan 16 '08 #7

P: n/a

"SurturZ" <su*****@newsgroup.nospamwrote in message
news:0F**********************************@microsof t.com...
My understanding is that in .NET, all strings with the same contents will
be
the same instance anyway.

So for example try the following code
Dim strA As String = "ABCDEF"
Dim strB As String = "ABCDEF"
MsgBox(String.ReferenceEquals(a, b))

It returns "True"!
This is true. Before a new string is made on the heap, the "intern pool" is
checked to see if it already is in the pool. If so, then the same string
object is used for the new variable, if not, a new string object is created
in memory. While this increases performance, it doesn't change the basic
ByVal/ByRef point.
Strings are now reference types, so whether you pass ByRef or ByVal, you
are
passing (or copying) a pointer, not the contents of the string itself.
Yes, but in one case you are making a copy of a pointer that points directly
at the object on the heap and in the other you are making a pointer that
points to the first pointer (which is slightly less efficient).
>
I think the reason is as old as the hills. Strings in BASIC have always
been
variable length, and Microsoft has always tried to hide Pointers, memory
addresses etc from BASIC programmers. Being variable length, you need
either
a terminator or a length field in memory so the computer knows where the
end
of the string is. But in the BASIC paradigm, the "whole variable" only
consists of the characters, so the language must hide the
terminator/length
field. The way VB does this is by making strings Reference types, then
making
strings immutable and non-repeating. So if you do the comparison
If strA = strB Then ...
technically you are comparing REFERENCES (ie. that they point to the same
part of memory) rather than comparing the contents of the variables.
--
David Streeter
Synchrotech Software
Sydney Australia
"Siegfried Heintze" wrote:
>Why does VB.NET V2 force me to pass by value for my set function? When I
try
to change it to const byref it gives me a syntax error. It seems very
inefficient to be passing strings around by value when a reference to a
constant string object will do fine (all we are going to do is copy it).
In
my case, would the byval for the set function cause a superfluous copy?
Thanks,
Siegfried

class person
dim m_name as string
public sub new (n as string)
m_name = n
end sub
public property name () as string
Get
return m_name
end get
set ( const byref value as string)
m_name = value
end set
end Property
public overloads overrides function ToString() as string
return m_name
end function
protected overloads overrides sub Finalize()
outp.WriteLine("~" & name )
MyBase.Finalize()
end sub
End Class

Jan 16 '08 #8

P: n/a
Siegried,

It is always more efficient (in a matter of processing) to pass something by
value then by reference.
By Reference means nothing more than that the By value reference is placed
in a box.

However the behaviour of a type (by instance a string is immutable) can make
that you need sometimes to pass by reference.

Cor
Jan 16 '08 #9

P: n/a
Scott M. wrote:
"SurturZ" <su*****@newsgroup.nospamwrote in message
news:0F**********************************@microsof t.com...
>My understanding is that in .NET, all strings with the same contents
will be the same instance anyway.

So for example try the following code
Dim strA As String = "ABCDEF"
Dim strB As String = "ABCDEF"
MsgBox(String.ReferenceEquals(a, b))

It returns "True"!

This is true. Before a new string is made on the heap, the "intern
pool" is checked to see if it already is in the pool. If so, then
the same string object is used for the new variable, if not, a new
string object is created in memory.
Are you entirely sure about that? As I understand it, the COMPILER does that
at compilation time, but at run-time no such thing occurs.

For example:

\\\
Dim a As String
Dim b As String

a = "ABCDEF"
b = "ABC"
b &= "DEF"

MsgBox(String.ReferenceEquals(a, b))
///

Unlike SurturZ's example, this displays False. The compiler doesn't see the
string assignment to variable "b" as being the same as to "a" at compile
time, and so the two strings exist separately in memory despite having the
exact same content.

--

(O)enone
Jan 16 '08 #10

P: n/a
Now if you were to use String.Intern on b, you'd get back to a reference to
a. The intern table is used for constant strings, not dynamically created
strings. to use it for dynamically created strings, you need to do the
interning manually
"(O)enone" <oe****@nowhere.comwrote in message
news:fm**********@aioe.org...
Scott M. wrote:
>"SurturZ" <su*****@newsgroup.nospamwrote in message
news:0F**********************************@microso ft.com...
>>My understanding is that in .NET, all strings with the same contents
will be the same instance anyway.

So for example try the following code
Dim strA As String = "ABCDEF"
Dim strB As String = "ABCDEF"
MsgBox(String.ReferenceEquals(a, b))

It returns "True"!

This is true. Before a new string is made on the heap, the "intern
pool" is checked to see if it already is in the pool. If so, then
the same string object is used for the new variable, if not, a new
string object is created in memory.

Are you entirely sure about that? As I understand it, the COMPILER does
that at compilation time, but at run-time no such thing occurs.

For example:

\\\
Dim a As String
Dim b As String

a = "ABCDEF"
b = "ABC"
b &= "DEF"

MsgBox(String.ReferenceEquals(a, b))
///

Unlike SurturZ's example, this displays False. The compiler doesn't see
the string assignment to variable "b" as being the same as to "a" at
compile time, and so the two strings exist separately in memory despite
having the exact same content.

--

(O)enone
Jan 16 '08 #11

P: n/a
Oh, and I forgot to mention, technically the interning of constant strings
is not done by the compiler, rather it is done by the JIT/runtime. You can
turn off string interning of constants by ngen'ing the assembly when you
have a no interning attribute in the assembly.
<Assembly:
CompilationRelaxationsAttribute(CompilationRelaxat ions.NoStringInterning)>

So yes it is the compiler, but the JIT or ngen compiler not the vbc or csc
compilation ;)

"Bill McCarthy" <Bi**@NOSPAM.comwrote in message
news:4D**********************************@microsof t.com...
Now if you were to use String.Intern on b, you'd get back to a reference
to a. The intern table is used for constant strings, not dynamically
created strings. to use it for dynamically created strings, you need to do
the interning manually
"(O)enone" <oe****@nowhere.comwrote in message
news:fm**********@aioe.org...
>Scott M. wrote:
>>"SurturZ" <su*****@newsgroup.nospamwrote in message
news:0F**********************************@micros oft.com...
My understanding is that in .NET, all strings with the same contents
will be the same instance anyway.

So for example try the following code
Dim strA As String = "ABCDEF"
Dim strB As String = "ABCDEF"
MsgBox(String.ReferenceEquals(a, b))

It returns "True"!

This is true. Before a new string is made on the heap, the "intern
pool" is checked to see if it already is in the pool. If so, then
the same string object is used for the new variable, if not, a new
string object is created in memory.

Are you entirely sure about that? As I understand it, the COMPILER does
that at compilation time, but at run-time no such thing occurs.

For example:

\\\
Dim a As String
Dim b As String

a = "ABCDEF"
b = "ABC"
b &= "DEF"

MsgBox(String.ReferenceEquals(a, b))
///

Unlike SurturZ's example, this displays False. The compiler doesn't see
the string assignment to variable "b" as being the same as to "a" at
compile time, and so the two strings exist separately in memory despite
having the exact same content.

--

(O)enone
Jan 16 '08 #12

P: n/a
In article <0F**********************************@microsoft.co m>,
SurturZ <su*****@newsgroup.nospamwrote:
So if you do the comparison
If strA = strB Then ...
technically you are comparing REFERENCES (ie. that they point to the same
part of memory) rather than comparing the contents of the variables.
This is incorrect.

Microsoft.VisualBasic.CompilerServices.StringType. StrCmp is used for
the = < and operators.

--
J.B. Moreno
Jan 17 '08 #13

P: n/a

"J.B. Moreno" <pl***@newsreaders.comwrote in message
news:16**********************@newsreaders.com...
In article <0F**********************************@microsoft.co m>,
SurturZ <su*****@newsgroup.nospamwrote:
> So if you do the comparison
If strA = strB Then ...
technically you are comparing REFERENCES (ie. that they point to the same
part of memory) rather than comparing the contents of the variables.

This is incorrect.

Microsoft.VisualBasic.CompilerServices.StringType. StrCmp is used for
the = < and operators.
That's true. If you wan to compare the two variables to see if they point
to the same object in memor, use the "Is" operator.

>
--
J.B. Moreno

Jan 18 '08 #14

P: n/a
In article <##**************@TK2MSFTNGP05.phx.gbl>,
Scott M. <sm**@nospam.nospamwrote:
"J.B. Moreno" <pl***@newsreaders.comwrote in message
SurturZ <su*****@newsgroup.nospamwrote:
So if you do the comparison
If strA = strB Then ...
technically you are comparing REFERENCES (ie. that they point to the same
part of memory) rather than comparing the contents of the variables.
This is incorrect.

Microsoft.VisualBasic.CompilerServices.StringType. StrCmp is used for
the = < and operators.

That's true. If you wan to compare the two variables to see if they point
to the same object in memor, use the "Is" operator.

While that's true, it's less important than the fact that you can have
more than one instance of a string with the same value.
IF "1234".SubString(1,2) IS "1234".SubString(1,2) THEN
' never going to happen
END IF

SurturZ was confused by the fact that there will only be one instance
of a string CONSTANT in a namespace.

So that if you say

Dim str1 as String = "1234"
Dim str2 as String = "1234"

IF str1 IS str2 THEN
'this happens
END IF
But that's because what's really happening under the hood is:

DIM cStr1234 AS String = "1234"

Dim str1 as String = cStr1234
Dim str2 as String = cStr1234

IF str1 IS str2 THEN
'this happens
END IF

On a somewhat related note, if you use Option Compare Text and then
compare "a" to "A" the answer could be true for you and false for
someone else, without a single change in the program.

--
J.B. Moreno
Jan 20 '08 #15

This discussion thread is closed

Replies have been disabled for this discussion.