How to prevent passed value types from being changed

  • Thread starter Thread starter Tony Johansson
  • Start date Start date
Peter said:
Unfortunately, anyone who thinks that this discussion is about a proposal
to add a feature to C# that is like "const" arguments and functions in C++
has missed the point.

Just in case you are attempting to referee what this discussion is about:
This discussion will be about whatever the participants choose to discuss.
"const" is about the mutability of the object itself. "readonly" is only
about the variable. Tony's question is clearly only about the variable,
and even reference type variables marked as "readonly" would say nothing
at all about the object itself; only the variable referencing the object
is affected.

Say what? C++ allows you to apply const to individual arguments.
There have been a number of tangential replies that really are about
something completely different from what Tony's asking about. IMHO, it's
important to understand that for anyone that intends or claims to be
addressing Tony's own original question.

And?

Jonathan
 
Jonathan said:
Just in case you are attempting to referee what this discussion is
about: This discussion will be about whatever the participants choose to
discuss.

I'm not refereeing anything. But there are several people who have
replied to this thread, making claims (implicit or explicit) that their
comments pertain to Tony's question, when in fact they don't.

As long as it's understood that those comments have nothing to do with
Tony's question, there's no problem at all. You guys can go off on
whatever tangents you want.

Just don't think that you're talking about "readonly" in C#, and for
heaven's sake don't try to claim you are, because you'll just confuse
people who don't know better (possibly even yourselves).
Say what? C++ allows you to apply const to individual arguments.

Yes, but it's not the value of the parameter that is affected.
"readonly" in C# is about the variable itself. "const" in C++ as
applied to parameters is about what you can _do_ with the value of the
parameter, and has nothing to do with what that value of the parameter
itself is.

"readonly" in C#: not allowed to change the value of the variable;
mutating the object is fine.

"const" in C++: not allowed to mutate the object (unless of course you
cast away the "const")

If you are talking about "const" in C++, you are not talking about
"readonly" in C#. And Tony's question was about "readonly" in C#.

Pete
 
Unfortunately, anyone who thinks that this discussion is about a
proposal to add a feature to C# that is like "const" arguments and
functions in C++ has missed the point.

"const" is about the mutability of the object itself. "readonly" is only
about the variable.

????

The effect of const entirely depends on whether it is:

void M(const C *o)

or:

void M(C *const o)

Arne
 
Arne said:
The effect of const entirely depends on whether it is:

void M(const C *o)

or:

void M(C *const o)

I am clearly talking about the former usage, as that's the behavior
being raised by others in this thread.

Conversely, if we are to imagine that people are discussing the latter
usage, then it doesn't make sense for someone to suggest that "readonly"
applied to a method parameter isn't useful and yet to use the C++
"const" as an example, since the latter usage contradicts their claim.

So, take your pick: either it's obvious which usage is being discussed,
or the usage being discussed is contradicting the people discussing it.

Either way, it adds nothing to the question Tony had.

Pete
 
I am clearly talking about the former usage, as that's the behavior
being raised by others in this thread.

Conversely, if we are to imagine that people are discussing the latter
usage, then it doesn't make sense for someone to suggest that "readonly"
applied to a method parameter isn't useful and yet to use the C++
"const" as an example, since the latter usage contradicts their claim.

So, take your pick: either it's obvious which usage is being discussed,
or the usage being discussed is contradicting the people discussing it.

Either way, it adds nothing to the question Tony had.

That is correct.

But I think it is very relevant to point out that your
claim:

#"const" is about the mutability of the object itself.

is just plain wrong.

No need to give people incorrect C++ information even in a C# group.

Arne
 
Yes, but it's not the value of the parameter that is affected.

"readonly" in C# is about the variable itself. "const" in C++ as applied
to parameters is about what you can _do_ with the value of the
parameter, and has nothing to do with what that value of the parameter
itself is.

"readonly" in C#: not allowed to change the value of the variable;
mutating the object is fine.

"const" in C++: not allowed to mutate the object (unless of course you
cast away the "const")

If you are talking about "const" in C++, you are not talking about
"readonly" in C#. And Tony's question was about "readonly" in C#.

Your understanding of const in C++ is wrong.

Const in C++ can apply to both the object and the variable.

And there are specific syntax for each.

Arne
 
Arne said:
[...]
But I think it is very relevant to point out that your
claim:

#"const" is about the mutability of the object itself.

is just plain wrong.

I'd say "incomplete" rather than "just plain wrong". But, whatever…
No need to give people incorrect C++ information even in a C# group.

It is true, I assumed the people involved would understand that I am
talking about the specific usage of "const" being discussed here.
You're correct though, if someone not involved with the discussion at
hand saw that statement, they may take away the wrong understanding.

Perhaps that was a bad assumption to make, and if I've confused anyone,
I apologize for that.

Pete
 
Peter said:
Yes, but...

Then why did you say const was only about the "mutability of the object
itself" as opposed to being about the variable?
"readonly" in C#: not allowed to change the value of the variable;
mutating the object is fine.

"const" in C++: not allowed to mutate the object (unless of course you
cast away the "const")

Which object? If a method argument is declared using const, that specifies
that the method cannot modify the argument. It makes no restrictions on
whether or not the method can make changes to member variables.

Jonathan
 
Then why did you say const was only about the "mutability of the object
itself" as opposed to being about the variable?


Which object? If a method argument is declared using const, that
specifies that the method cannot modify the argument. It makes no
restrictions on whether or not the method can make changes to member
variables.

No.

It all depends on whether it is:

void M(const C *o)

or:

void M(C *const o)

Arne
 
What's no? Whichever part of the argument const is applied to cannot be
changed.

Please try and be more specific.

Jonathan
 
What's no? Whichever part of the argument const is applied to cannot be
changed.

Please try and be more specific.

In the first case o can be changed but what o points to can
not be changed.

In the last case o can not be changed but what o points to
can be changed.

Your description only fits the last case.

Arne
 
In the first case o can be changed but what o points to can
not be changed.

In the last case o can not be changed but what o points to
can be changed.

Your description only fits the last case.

And Peters description fits the first case.

So obviously you can't agree, because you are discussing
two completely different things.

Arne
 
Peter Duniho said:
Unfortunately, anyone who thinks that this discussion is about a
proposal to add a feature to C# that is like "const" arguments and
functions in C++ has missed the point.

It seems to me that you're the only one that thinks people are making
proposals.

The OP may have been making a proposal, but if so it was in a rather
trollish manner, taken at face value he was asking if a feature exists
and the answer he was given was "no".

As for me, I wouldn't propose the OP's feature as described for
implementation if you paid me, and I wouldn't propose either of the two
somewhat related features that I described *unless* you did. The first
is IMO unnecessary in C#, as for the second, while declaring a
reference type immutable inside a particular method doesn't sound dumb,
I can't bring to mind an occasion when I needed/wanted it.
 
Arne said:
In the first case o can be changed but what o points to can
not be changed.

No kidding?
In the last case o can not be changed but what o points to
can be changed.

Your description only fits the last case.

In that case, you should've said you want to clarify what was said, and "no"
was in incorrect response.

Jonathan
 
It seems to me that you're the only one that thinks people are making
proposals.

The OP may have been making a proposal, but if so it was in a rather
trollish manner, taken at face value he was asking if a feature exists
and the answer he was given was "no".

As for me, I wouldn't propose the OP's feature as described for
implementation if you paid me, and I wouldn't propose either of the two
somewhat related features that I described *unless* you did. The first
is IMO unnecessary in C#, as for the second, while declaring a
reference type immutable inside a particular method doesn't sound dumb,
I can't bring to mind an occasion when I needed/wanted it.

J.B., would wanting to pass an array containing a translation table of

some sort be such an example? If the called method could accept a
an array parameter, to allow different tables to be passed, you might
want to be able to describe that the array contents itself are not to
be changed by the routine. You said "reference type", as opposed to
just "reference", which is why I mention an array.
I am no C++ expert, but even in simple C one can declare that the
formal parameter is const, the object referred to by the formal
parameter is const (but not the parameter itself), or that both
or neither are const.

I have been following this thread and must admit that at first I
did not understand Pete's insistence that "const" != "readonly",
which it _can_ be when applied to the parameter and not object
to which the parameter refers.

I think _some_ sort of "adornment" or enhancement to the readonly
machinery would be very useful, both in the case of parameter
passing as well as to be able to declare an array of constant
values as we can in vanilla C, i.e.,
const int myarr[] = {1,2,3,4,5};
without the various "techniques"/workarounds (I would say jumping
through hoops) of hiding them in classes and having to provide
either indexers, or, in the case of static arrays, /get/ accessors.

Or perhaps I have missed the point too.

oz
 
ozbear said:
J.B., would wanting to pass an array containing a translation table of
some sort be such an example?

Possibly, but...
If the called method could accept a an array parameter, to allow
different tables to be passed, you might want to be able to describe
that the array contents itself are not to be changed by the routine.

....this is where the feature falls down. The "are not to be changed by
the routine" implies that this is a statement by the caller, and the
caller can NOT say that. The method *being* called can say "I promise
that I won't change the contents of the array", but the caller can't
impose that requirement on arbitrary method calls. Even using
something like AOP the best it could do would be to throw an exception
at runtime, not when compiling.

At compile time the compiler could warn about the method call, saying
it doesn't know if the method will change the contents or not, but
what's the use of that?

So, there's a chicken and egg problem, no code currently has such an
attribute, which means that adding it a bit at a time is likely to be a
pain (you add it to method, but it calls a method that doesn't have it,
so you have to add it to that method as well and so forth and so on,
and then you run into a method that uses reflection and you can't use
it at all). And then there's method's that you didn't write, either
framework or 3rd party, where you can't say for sure whether or not
they violate the contract.

And if you step back from that a bit, you have to ask yourself a
fundamental question: why am I worried about the method changing the
contents?
You said "reference type", as opposed to just "reference", which is
why I mention an array. I am no C++ expert, but even in simple C one
can declare that the formal parameter is const, the object referred
to by the formal parameter is const (but not the parameter itself),
or that both or neither are const.

I'm no C++ expert either, but I see where this feature would be useful
in C++ -- handles and pointers. C++ doesn't really have reference
types, it just has pointers, which are notoriously fragile and error
prone. Adding something to make them less error prone is useful. But
C# HAS reference types and so avoids the confusion caused by pointers.
 
Back
Top