3

I want to use clean and less coded class with automatic properties. All of properties are public. Inside a methods in same class I also used that properties. So, I think that this approach is mashable because I use public properties for internally usage and for a public usage. What is best approach with situation like this one? Use private members inside methods and create properties for public usage or use public (or in some special situation private) properties inside class?

public class Account
{
     public int Count {get; set;}

     private int Calculate()
     {
         return Count * Count;
     }
}

or use something like this

public class Account
{
     private int _count;
     public int Count {
        get
        {
            return _count;
        } 
        set
        {
            _count = value,
        }
     }

    private int Calculate()
    {
        return _count * _count;
    }
}
Raphaël Althaus
  • 59,727
  • 6
  • 96
  • 122
SilverDeveloper
  • 187
  • 2
  • 13

5 Answers5

2

The first way is perfectly fine, as it effectively is what you wrote in your second way. However, be careful when you need to add additional code to either getter or setter.

Femaref
  • 60,705
  • 7
  • 138
  • 176
2

It is perfectly acceptable to use the public property internally as well as externally, especially if it is an automatic property because there is no logic in your property. And I think it is the preferred method since it is cleaner code.

BTW: When your code is compiled a backing field is created so the IL code for both examples is the same. So automatic properties are simply a design-time developer usability feature.

IL code for getter of automatic property...

.method public hidebysig specialname instance int32 
    get_Count() cil managed
{
  .custom instance void [mscorlib]System.Runtime.CompilerServices.CompilerGeneratedAttribute::.ctor() = ( 01 00 00 00 ) 
  // Code size       11 (0xb)
  .maxstack  1
  .locals init (int32 V_0)
  IL_0000:  ldarg.0
  IL_0001:  ldfld      int32 ConsoleApplication1.Program::'<Count>k__BackingField'
  IL_0006:  stloc.0
  IL_0007:  br.s       IL_0009
  IL_0009:  ldloc.0
  IL_000a:  ret
} // end of method Program::get_Count

IL code for getter of property with backing field ...

.method public hidebysig specialname instance int32 
    get_Count() cil managed
{
  // Code size       12 (0xc)
  .maxstack  1
  .locals init ([0] int32 CS$1$0000)
  IL_0000:  nop
  IL_0001:  ldarg.0
  IL_0002:  ldfld      int32 ConsoleApplication1.Program::_count
  IL_0007:  stloc.0
  IL_0008:  br.s       IL_000a
  IL_000a:  ldloc.0
  IL_000b:  ret
} // end of method Program::get_Count
Gene S
  • 2,735
  • 3
  • 25
  • 35
2

I think the first method is preferable. You're exposing a concept, rather than a simple variable, which means you can easily change the definition of that concept at a later date without changing the consuming code.

In fact, I wish there was a way to make fields accessible only to the property which requires them, to explicitly avoid the second case.

Ian Newson
  • 7,679
  • 2
  • 47
  • 80
0

Don't see a problem here, I mean in using public properties internaly. It's well-known that properties introduce some very tiny overhead in respect of fields, but in 99.99% cases it's irrelevant, so I don't think it's important here.

In short, the first case is ok.

Think also about this in terms of TDD design. If you're going to test public members (according to the best practices of TDD), you would also be capable to test impact om "internal" functionality too.

Tigran
  • 61,654
  • 8
  • 86
  • 123
0

Getters and Setters are highly overused. I’ve seen millions of people claiming that public fields are evil, so they make them private and provide getters and setters for all of them. I believe this is almost identical to making the fields public, maybe a bit different if you’re using threads (but generally is not the case) or if your accessors have business/presentation logic (something ‘strange’ at least). I’m not in favor of public fields, but against making a getter/setter (or Property) for everyone of them, and then claiming that doing that is encapsulation or information hiding… ha! by Pablo Fernandez ref: this and 19 other controversial programming opinions

To address the question, I've used both and the first option is the simplest. It is when some side effect occurs within the property getter/setter that the question is a little more difficult to answer. A typical example is when an event is raised to indicate the property has changed. Is that something that can occur both within the class and from an external request? In that case using the property rather than the backing variable will give consistent behaviour. So the best answer is it depends :-)

David Clarke
  • 12,888
  • 9
  • 86
  • 116
  • I realize the quote above is from somebody else but I do not agree with it. Consistency is important for ease of maintenance. If the standard practice is that either one is acceptable then inconsistency will clutter the code. So my opinion is, at least the property getter or setter should be public (if neither is public is should not be a property), properties should always be PascalCase, fields should always be private and should always be camelCase. IMHO – Gene S Sep 07 '12 at 13:10
  • I realise the quote was potentially inflammatory but rather than accept conventional wisdom at face value it's often useful to get a different perspective. I use automatic properties pretty much everywhere, then if I do need to add some logic to a getter or setter it is easy to add a backing var as suggested by @Ian Newson. A private field is really just a private member variable. Check out http://stackoverflow.com/a/653799/132599 for some differences between properties and fields. – David Clarke Sep 09 '12 at 21:24