accessor pairs - bad examples abound?

K

Kavvy

How come a lot of the examples I have seen on the net define accessor pairs
within a class, and then only ever use the accessor outside the class? When
used within the class the variable is accessed directly.

Is there something I'm missing about this? To reduce code re-writing it is
(I thought) standard practice to use accessor pairs in the class that
defines them as well as outside.

This becomes apparent if you need to perform checks on a new value before
assigning it to the variable. If you have 10 places where the variable is
directly accessed within the class then you would have 10 places to update
your code. If using an accessor pair then you only have 1 place to update
you code.

Correct me if I'm wrong or missing something about C# accessor pairs.

Rich.
 
J

Jon Skeet [C# MVP]

Kavvy said:
How come a lot of the examples I have seen on the net define accessor pairs
within a class, and then only ever use the accessor outside the class? When
used within the class the variable is accessed directly.

Is there something I'm missing about this? To reduce code re-writing it is
(I thought) standard practice to use accessor pairs in the class that
defines them as well as outside.

That's *a* convention (and one which I like) but I don't think it
really counts as standard practice yet.

One thing I wish C# had was a way of declaring that the variable could
*only* be accessed through the property, to enforce this convention.
 
N

Niki Estner

Kavvy said:
How come a lot of the examples I have seen on the net define accessor
pairs
within a class, and then only ever use the accessor outside the class?
When
used within the class the variable is accessed directly.

IMO The most imporant aspect of properties is that they hide implementation
details of a class. There's no need to hide implementation details from the
implementation.
Is there something I'm missing about this? To reduce code re-writing it is
(I thought) standard practice to use accessor pairs in the class that
defines them as well as outside.

Of course you should use property accessors if you can reuse code that way.
But this really depends on what the accessors are doing. Just a few
examples:
- if the set-accessor updates some DB or GUI you might want to do one bulk
update for a complex operation, instead of many little updates for each
changed property
- a complex operation might change two of more variables, so the object
state might indeed be inconsistent during the operation
- it is also common that accessors only return interfaces instead of classes
(e.g. IEnumerable instead of ArrayList), so the actual implementation can be
changed without changing other classes; Operations inside the class might
need full access on the object.

Niki
 
P

Paul E Collins

Jon Skeet said:
One thing I wish C# had was a way of declaring that
the variable could *only* be accessed through the
property, to enforce this convention.

This seems difficult, because (to the compiler) there is no explicit
association between a property and the variable that it affects.
Indeed, setting a property might affect multiple variables in the
class, or even none (e.g. a property that sets another object's
property).

In the case of "simple properties" (ones that are just get/set
wrappers over private variables), I'd like to be able to declare them
with a single construct - perhaps using a new "property" modifier -
but this is obviously less flexible than the current system, where
accessors can contain arbitrary code.

P.
 
N

Niki Estner

Paul E Collins said:
This seems difficult, because (to the compiler) there is no explicit
association between a property and the variable that it affects.
Indeed, setting a property might affect multiple variables in the
class, or even none (e.g. a property that sets another object's
property).

You could declare the variable somewhere inside the property.
Like this

public int MyProperty
{
int myProperty;
get { return myProperty; }
set { myProperty = value; }
}

Actually I think instance-variables that are only visible to a scope of a
function or property would be handy in many cases.

Niki
 
N

Niki Estner

Paul E Collins said:
This seems difficult, because (to the compiler) there is no explicit
association between a property and the variable that it affects.
Indeed, setting a property might affect multiple variables in the
class, or even none (e.g. a property that sets another object's
property).

You could declare the variable somewhere inside the property.
Like this

public int MyProperty
{
int myProperty;
get { return myProperty; }
set { myProperty = value; }
}

Actually I think instance-variables that are only visible to a scope of a
function or property would be handy in many cases.

Niki
 
J

Jon Skeet [C# MVP]

Niki Estner said:
You could declare the variable somewhere inside the property.
Like this

public int MyProperty
{
int myProperty;
get { return myProperty; }
set { myProperty = value; }
}

Actually I think instance-variables that are only visible to a scope of a
function or property would be handy in many cases.

That's exactly what I'd be suggesting, yes.

Internally it would compile just to a private variable, but the
compiler would know not to let the class access that variable outside
the property.

You'd probably need some name-munging in there as well, and there are
"difficulties" involving serialization etc, but it's still something
I'd like to see explored.
 
D

Daniel O'Connell [C# MVP]

You'd probably need some name-munging in there as well, and there are
"difficulties" involving serialization etc, but it's still something
I'd like to see explored.

Hmm, what kind of difficulties do you see with serialization, specificatlly?
 
J

Jon Skeet [C# MVP]

Daniel O'Connell said:
Hmm, what kind of difficulties do you see with serialization, specificatlly?

To be honest, I can't remember at the moment - but I know that last
time I brought this up, someone gave some reasons why you'd need to
access the variables outside the properties.
 
D

Daniel O'Connell [C# MVP]

Jon Skeet said:
To be honest, I can't remember at the moment - but I know that last
time I brought this up, someone gave some reasons why you'd need to
access the variables outside the properties.

Hrmm, that is a curious question. Considering a matched pair of get\set
accessors, accessing the data couldn't be very hard.

I suppose something like
int field;
int ActualValue;
{
get
{
return field*2;
}
}

would be a pain, and the subgrouping does nothing for small groups of
properties that require access to the same field, but solving that is alot
more indepth.

A custom accessor might fix the serialization problems, say
serialize
{
return field;
}

and limit access to serialize_ to some method(s) that are marked as
serialization methods, but that does require a change to the language.
 
J

Jon Skeet [C# MVP]

Daniel O'Connell said:
Hrmm, that is a curious question. Considering a matched pair of get\set
accessors, accessing the data couldn't be very hard.

I suppose something like
int field;
int ActualValue;
{
get
{
return field*2;
}
}

would be a pain

Of course, making such a field "ultra-private" for the rest of the
class would make it rather difficult to be useful anyway. Perhaps it
should only be available for read/write properties?
and the subgrouping does nothing for small groups of
properties that require access to the same field, but solving that is alot
more indepth.

A custom accessor might fix the serialization problems, say
serialize
{
return field;
}

Hmm... possibly. I suspect that constructors might also need access - I
can imagine some cases where you want the actual property to be read-
only, but set up during construction.
and limit access to serialize_ to some method(s) that are marked as
serialization methods, but that does require a change to the language.

Well, it's all requiring a change to the language anyway :)
 
D

Daniel O'Connell [C# MVP]

Of course, making such a field "ultra-private" for the rest of the
class would make it rather difficult to be useful anyway. Perhaps it
should only be available for read/write properties?

Probably, except for readonly+constructor initalized as you mention below. I
actually forgot to write a set for that, but no matter, it is a potential
problem
Hmm... possibly. I suspect that constructors might also need access - I
can imagine some cases where you want the actual property to be read-
only, but set up during construction.

Yes, that is a very real issue to consider
Well, it's all requiring a change to the language anyway :)

LOL, yes, but a less drastic one. The major issue I'm concerned with is how
do you express the difference between direct field access and property
access if the field is scoped and accessible using a special accessor. You
could go whole hog and allow for a method-style modifier:
fieldof\valueof (ActualValue)
or you could simply allow access to the variable in select spots, or perhaps
allow for some other style of access(a psuedo-FieldValue field on the
property, perhaps?).

I don't like scoping a variable lexically and then allowing it to be
accessed in constructors and *some* methods without some sort of special
operation, it just isn't consistent. If the variable looks like its well
scoped, it just seems wrong to only actually enforce a weak scope. Without a
special operator(or set thereof), I don't think it would be terribly easy to
do. But, I could be wrong.

One idea I had toyed with was full blown acls, so you could do
int field
allow read in all,
allow write in ActualValue,Serialize, .ctor;

but that is alot of typing, even if it does bring exact accessibilty
granularity up quite a bit, beyond anything regular languages use, anyway.
That doesn't mean its a good idea, ;).
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Top