I have two tables in the database that are used almost for the same thing, but the tables don't have exactly the same structure.
Lets say I have one table for manual requests and another table for automatic requests. I have to load both tables into the same GridView and I'm using custom business objects.
To illustrate the question I'll call TManualReqTable and TAutomaticReqTable.
TManualReqTable
- ID
- Field1
- Field2
- Field3
- Field4
and
TAutomaticReqTable
- ID
- Field1
- Field3
In the code, I'm using the same object for these two tables. I have an interface with all the properties of both tables and I'm checking if the field exists when I'm loading the data to the object.
But I'm thinking this should be created with two objects and one superclass with abstracts methods.
What is your opinion about it?
I would create an interface IRequest that describes the fields & methods common to both, and then interfaces & classes for ManualRequest and AutomaticRequest that implement IRequest and also add the methods/fields unique to each of them.
You can use IRequest as the type for something that incorporates either one. When iterating through something that can include data from either, you can check whether each object implements the interfaces:
foreach (IRequest obj in RequestList) {
// do stuff that uses the common interface
if (obj is IManualRequest) {
// do stuff specific to manual requests
} else if (obj is IAutomaticRequest) {
// likewise
}
}
I follow a general rule to avoid creating base classes unless:
I've already designed or discovered sufficient commonality to give sufficient substance to the base class.
I have a use case for consuming the classes as the base class; if I don't have anything that can operate on the common functionality of the classes, there's little value in having a base class (can achieve the same functionality through composition of a class implementing the common behaviors.)
The requirements are sufficiently stable that I believe the base class abstraction will hold without significant modification in the future. Base classes become increasingly difficult to modify over time.
IMO, forget how the database looks like for a minute or two.
Think of how it should be structured as an object.
Think of how you would like to use that object. If you need to visualize, write some code of that yet non-existing object and tweak it until it looks elegant.
Think of how to make it happen.
model first development
Hope it helps.
well, there are a few assumptions i'm making here, so let me make them explicit...
given:
this is primarily a difference in query/display logic
the display logic can already handle the nulls
the underlying object being represented is the same between the two items
there's a simple way of determining whether this was a 'manual' or an 'automatic' call
i would say that inheritance is not the way i would model it. why? because it's the same object, not two different kinds of object. you're basically just not displaying a couple of the fields, and therefore do not need to query them.
so, i would probably try to accomplish something that makes clear the nature of the difference between the two (keep in mind that i intend this to show a way of organizing it so that it's clear, any particular implementation might have different needs; the main idea to glean is treating the differences as what they are: differences in what gets queried based upon some sort of condition.
public enum EQueryMode
{
Manual,
Automatic
}
public class FieldSpecification
{
public string FieldName { get; set; }
public bool[] QueryInMode { get; set; }
public FieldSpecification
(
string parFieldName,
bool parQueryInManual,
bool parQueryInAutomatic
)
{
FieldName = parFieldName;
QueryInMode = new bool[] { parQueryInManual, parQueryInAutomatic };
}
}
public class SomeKindOfRecord
{
public List<FieldSpecification> FieldInfo =
new List<FieldSpecification>()
{
new FieldSpecification("Field1", true, true),
new FieldSpecification("Field2", true, false),
new FieldSpecification("Field3", true, true),
new FieldSpecification("Field4", true, false)
};
// ...
public void PerformQuery(EQueryMode QueryMode)
{
List<string> FieldsToSelect =
(
from f
in FieldInfo
where
f.QueryInMode[(int)QueryMode]
select
f.FieldName
)
.ToList();
Fetch(FieldsToSelect);
}
private void Fetch(List<string> Fields)
{
// SQL (or whatever) here
}
}
edit: wow i can't seem to make a post today without having to correct my grammar! ;)
Related
I'm writing a permissions service for my app, and part of this service's responsibility is to check that a user has permission to access the particular object they are trying to change. There are around 6 six different objects that can be mutated, and they all possess a particular property called tenant. This tenant prop is what I need to check.
The issue is that I want to keep my code as DRY as possible, but I can't see anyway of not repeating myself in this particular situation. I have six different objects which I need to check, therefore I have six different IDs and six different calls to the database to retrieve the information I need.
I'm reluctant to write six different methods each supporting the different objects I need to check, but since the code is going to look something like the below (vastly simplified) I'm not sure if there's anything I can do differently.
public bool CheckUserHasPermissionForObject(string id)
{
var obj = _dataRepository.GetObjById(id);
var userHasPermission = UserHasPermission(obj);
return userHasPermission;
}
I was hoping delegate types would lend a hand here but I don't think they'll help either.
There are few options there.
Option 1: Using interfaces
You can create an interface class that has the property tenant:
// TODO: Rename this class
public interface IParentClass
{
string Tenant { get; set; }
}
Then derive all your six objects from that:
// TODO: Rename this class
public class ChildClass1 : IParentClass
{
public string Tenant { get; set; }
}
// TODO: Rename this class
public class ChildClass2 : IParentClass
{
public string Tenant { get; set; }
}
//... TODO: Derive the others as well
And then modify your method to check that property like this:
public bool CheckUserHasPermissionForObject(string id)
{
var obj = _dataRepository.GetObjById(id) as IParentClass;
var userHasPermission = UserHasPermission(obj);
return userHasPermission;
}
private bool UserHasPermission(IParentClass obj)
{
// TODO: Implement your check here
if (obj.Tenant == "Whatever")
{
// TODO: Implement your logic here
}
return false;
}
Option 2: Using reflections
You can get the value of the property called "tenant" of different objects with reflections like this:
var tenantValue = obj.GetType().GetProperty("tenant").GetValue(obj, null);
This will try to find a property called "tenant" in any object, and return the value.
P.S. Option 3 might be using some generics, but not sure, as the question is not that clear at this moment.
The issue is that I want to keep my code as DRY as possible, but I can't see anyway of not repeating myself in this particular situation. I have six different objects which I need to check, therefore I have six different IDs and six different calls to the database to retrieve the information I need.
If the logic for checking permissions is not the same, then by definition you aren't repeating yourself. Don't make your code arcane or unreadable all in the name of DRY.
Because you're making 6 distinct calls to the database, your options for reusing code are limited.
I'm reluctant to write six different methods each supporting the different objects I need to check.
If the objects have different ways to verify the permissions, there is no way around this. Either the objects are all the same (and can inherit some sort of shared logic), or they aren't. Objects that look similar but aren't actually the same should be kept separate.
My recommendation
In order to communicate similar functionality (but different implementation), I'd use an interface. Maybe something like
public interface IUserPermission
{
string Tenant { get; set; }
bool CheckUserHasPermissions(string id);
}
This interface makes the calling code more consistent and better communicates how the objects are meant to interact. Notably, this does not reduce the amount of code written. It just documents/explains the intention of the code.
Alternative solution
Ultimately, the code will need to be able to distinguish your different types of objects. But technically you could write one giant function that switches based on object type instead of splitting the logic across the six different objects. I personally find this organization hard to read and debug, but you could technically write some sort of utility (extension) method like this:
public static bool CheckUserHasPermissions(this object obj, string id)
{
if (obj is Type1)
return CallDatabase1(id);
if (obj is Type2)
return CallDatabase2(id);
throw new ArgumentException("Unsupported object type.", nameof(obj));
}
Closed. This question needs details or clarity. It is not currently accepting answers.
Want to improve this question? Add details and clarify the problem by editing this post.
Closed 6 years ago.
Improve this question
I really don't know what to put in the title, so don't read too much into it.
Anyway, to explain what I'm having trouble with is this. I have three classes: A, B and C. The class hierarchy is as follows:
A <-- B <-- C
(So A is the base class.)
The application in question is a database app. It queries information several tables (A is one table, and B and C are one) and stores it into an instance of C. That part works fine. The problem is when I want to update the table represented by B and C.
To avoid boilerplate code for each code, I use reflection to generate an update query from the class. But if I pass it an instance of a C class, it means it will also pick all the members from A, which is a separate table. Hence the update query will be wrong. And that's where my problem lies. I
want to get all members of B and C without writing a lot of boilerplate code and with a clean, scalable solution. I just don't know how.
(I currently use an approach where I pick all members of the top-level type, then search all of the class's parents and pick all those members and stop collecting members when it finds a specific parent type, e.g. A. This is an awful solution, I think.)
All these classes contains variables fetched from the database and have no methods or fields. Any good ideas on how to approach this problem? I hear C# does not have multiple inheritance, a tool perfect for this job (thanks C#!).
I hope I'm making myself clear.
EDIT1:
To address some questions and give additional context. First off, here's how my system looks today. To query data, I first have a class X, and a query text. The query is run against the database and returns some rows. Then each row is converted into an instance of X and added to a list. The code knows how to convert a row into an X by using reflection and looking at the actual variables in X and the name of the columns in the fetched database row. It then takes column A and places that information into the variable called A in X. So by making a class X and matching that to the database structure is all that's necessary to fetch another table of data.
Sometimes you need to fetch data from multiple tables and put them together. To do this, I need a class X that matches the information fetched from the query. There are a lot of data that I fetch and all this data has a common subset fetched from table A. The rest is fetched from a lot of other tables that contain additional data. Hence the type system always looks like something A <-- B, where A is the common subset of all data I fetch. This works great for queries. I can add additional data and a class and I'm done. No more boiler plate code.
But that's only half the story. I need to update these tables too (I don't need to update A). But to do that, I need to separate the data fetched from the table A, the common subset. Here's how I do the updating:
Connection.RunUpdateQuery(..., Utility.ToDictionary(Entry));
Where Entry is the class containing the information to update into the target table. So I convert the class into a Dictionary representing column name, column value and send that the RunUpdateQuery which generates an update sql statement and sends it to the database. Again, this is really nice because I have to write absolutely no boilerplate code.
But Utility.ToDicionary can't know what subset of information I actually want to insert. What it does is just take every variable in the class and transform it into a dictionary where the name of the variable is the column name (i.e. the key of the dictionary). In this case, if I pass it a C, I really only just want B and C because they're part of the target table I want to update. The A subset is part of another table which I don't want to update.
If there's a framework that does all this work, I'm all for it. But right now, I don't have the time to rewrite this code. So I'm going to have to wait with that that until later.
This is also my own database that I am designing. I'm in charge of everything regarding the project's design.
I really don't want to generate queries, even if it just means running a tool because a) it means more work every time the database changes and b) it means more bugs because I might forget to update certain places when something changes. With my current reflection-based solution, I don't have to change anything. I just have to design the database and an appropriate class (which I have to anyway since I need to translate the rows from the db into appropriate first-class citizens in the code so I can work with them more easily).
Using attributes doesn't seem like a good way of doing it either because it's all context-dependent. The caller that wants to update a table must be able to choose which fields should be updated in the database, but not at such a fine-grained level. The caller should simply be able to select the class to update, so to speak.
Maybe this gives some clarity into my problem.
EDIT2:
Examples of class A, B, C:
C:
public class PumpEntry: SignalEntryD
{
public uint? Addr;
public uint MasterlistIdx;
public bool MinDominant;
public uint? TriggerInterval;
public uint? SpDef;
public uint? MinDef;
public uint? MaxDef;
public uint? Step0Def;
public uint? Step1Def;
public uint? Step2Def;
public uint? Step3Def;
public uint? Step4Def;
public uint? Step5Def;
public uint? ExReqFacBACNet, ExSpFacBACNet;
public decimal? DeltaTX0Def, DeltaTX1Def, DeltaTX2Def, DeltaTX3Def;
public uint? DeltaTYMinDef, DeltaTY0Def, DeltaTY1Def;
public string DeltaTSensor1, DeltaTSensor2;
public int? ReqLimitMethodDef;
}
B:
public class SignalEntryD: DeviceEntry
{
public int? Channel;
public int? pCOeNum;
}
A:
public class DeviceEntry: DbType
{
public int Id;
public DeviceType Type;
public string Name;
public string CMCategory;
public bool Generate;
public new string ToString() { return Name; }
}
You should probably use an ORM library such as Entity Framework or NHibernate. They know how to deal with inheritance (they offer several strategies you can choose from). Then you don't need to write any boilerplate code at all.
I guess the typical C# solution for this is to mark your fields with custom attributes, and use that in reflection to decide whether or not it should be included.
public class DoSerializeAttribute : Attribute {}
public class C : B {
[DoSerialize]
public MyMember { get; set; }
}
And later in your reflexion code you can use GetCustomAttribute method.
You say you are using reflection. In thise case, doing this:
C myObject = new C();
myObject.GetType().GetProperties(System.Reflection.BindingFlags.Public
| System.Reflection.BindingFlags.Instance
| System.Reflection.BindingFlags.DeclaredOnly)
Should only give you the properties declared specifically in C, not in B or A. From there on you could use myObject.GetType().BaseType which would give you B, and its BaseType would be A.
Check it in this fiddle
I made a rough query generator here: check it in this other fiddle, which generates all update queries needed (if you pass a C, it'll generate queries for tables A, B and C), except for the types you pass as parameters.
With this information, you could easily generate your update queries dynamically and for any levels of hierarchy.
I'd give you more specific code but you wrote none
Not saying this is the perfect solution, but it's what you are asking for in your question
Without learning ORM (which is a proper thing, but may be overkill in a simple case and by saying overkill I mean learning curve) you can use LINQ-to-SQL as model to access your data instead of creating C class yourself. Create dbml file (see e.g. here regarding what is it). As result you get you table class code-generated, then you just use it
using (var context = new SomeContext()) // static connection string
{
var query = context.SomeTable.AsQueryable();
if (SelectedFilter == Today)
query = query.Where(o => o.Id >= DateTime.Today);
...
// constructing ViewModel items (WPF, MVVM)
foreach (var item in query)
items.Add(new Item()
{
Id = item.Id,
...
}
}
Item (B in your example) is a simple class to hold values. You can populate other properties of Item using another query or context (another table or database).
When you want to update database you simply do
using (var context = new SomeContext())
{
var change = context.SomeTable.First(o => o.Id == item.Id);
change.Comment = item.Comment;
...
context.SubmitChanges();
}
Basically you write those methods once for your ready-made ViewModel item (can be a complicated query to many tables or multiple queries to different databases). Updating part can be methods of Item or, better, of ViewModel (because it can be optimized, e.q. when only changing Comment you don't need to update other fields and perform other queries).
Boilerplate? Not really, look into SomeContext generated cs-file to see some.
To be frank, I personally think your current solution is a mess. There are infinte amount tools available for this kind of stuff, why reinvent (and very badly to be honest) the wheel?
Anyhow, trying to solve your issue in your particular setup, here is what I'd do:
First off, get rid of inheritance. You shouldn't be using it at all. Inheritante is most definitely not a tool meant to be used as a means to avoid data duplication, the simple notion is horrendous.
You have 2 distinct tables in your DB, code them as such.
DbType
PumpEntry
I have no idea why you need the intermediate SignalEntryD. If its not a table in your DB then it shouldn't appear anywhere in your code (I'm guessing its also due to code duplication).
Be consistent: if fields Channel and pCoeNum are duplicated throughout different tables in your database then just duplicate them in your entities. Otherwise, create a table in your DB and then model it in your entities (as you do with DbType). Don't mix things up, do it the same way on both ends.
For reasons that become clear later on, make both your entities implement a "dummy" interface ITable (type safety) and a default parameterless constructor (including all your properties / fields of course).
Now the problem is, if I understand correctly, that you are receiving a Dictionary<string, object> with user updated values and you need to update a given table, the problem being that the dicitonary can contain fields that belong to different tables (I won't get into how you ended up with this problem to begin with, I'll just ride along...).
Well then, simply create a way to build any entity from a random dicitionary using reflection (my code uses properties, but it is equivalent with fields):
public static T CreateTable<T>(IDictionary<string, object> values) where T: ITable, new()
{
var table = new T();
foreach (var propInfo in typeof(T).GetProperties())
{
if (values.ContainsKey(propInfo.Name))
{
propInfo.SetValue(table, values[propInfo.Name]);
}
}
return table; //note that any property not defined in the dictionary will be initialized to the field's type default value.
}
And now, you'd use it as follows:
Connection.RunUpdateQuery(..., CreateTable<TableC>(Utility.ToDictionary(Entry))); //only fields of TableC will be passed along.
I'm modifying an app for performance gains. The app has a class with many properties. Typically this class is populated in its entirety by a primary key that pulls a large query from a database. The application is in great part slow because this happens constantly throughout, even though much of the time only one two properties in the class are needed in a given section of code. The existing large class has only a default constructor and all of its properties are nullable or have default values. In code below ignore lack of constructors and how these objects are populated.
public class Contract
{
public enum ContractStatus
{
Draft, Active, Inactive
}
private Int32 contractId = DALC.DefaultInt32;
private String name = DALC.DefaultString;
private ContractStatus status;
private ContractType contractType = null;
private CurrencyType currencyType = null;
private Company company = null;
}
As you can see it has its own properties, and also references other classes (e.g. ContractType, Company).
A few approaches I've thought of in light of common design patterns:
1) re-factor this hugely and break up those smaller sub-sections into their own classes with their own properties. Then reconstruct that large class with all of the smaller ones when it is needed. This will be quite laborious, though even if it sounds ideal and consistent with SOLID OOD principles.
2) Create new classes that simply contain the large class, but only expose one or two of its properties. I'm still creating a full blown version of the original, large class, but I will only populate the data I need. This will be via simple DB query, thus the bulk of the class will sit there unused and its null default classes it's referencing won't ever be constructed.
public class ContractName
{
Contract contract;
public ContractName()
{
contract = new Contract();
}
public String Name
{
get { return contract.Name; }
set { contract.Name = value; }
}
}
3) Add new constructors to existing large class with a parameter indicating what chunks of code I want to actually populate. This sounds messy and kind of nasty and wrong, and would leave me in the scenario where if Contract is created by a contract ID in one section of code it has different info than if created by contract ID elsewhere.
Thanks for any ideas!
I would recommend option 1: extract the classes you think you need to extract now. The other two options are just adding more technical debt which will take even longer to resolve in the future. Well-factored code is usually much easier to optimise than big complicated classes.
In my experience, breaking up classes is not all that laborious. In fact I usually find myself surprised by how quickly I can execute refactorings like Extract Class as long as I follow the recipe.
I have a business model with many classes in, some logical entities within this model consist of many different classes (Parent-child-grandchild.) On these various classes I define constraints which are invariant, for example that the root of the composite should have a value for Code.
I currently have each class implement an interface like so...
public interface IValidatable
{
IEnumerable<ValidationError> GetErrors(string path);
}
The parent would add a validation error if Code is not set, and then execute GetErrors on each child, which in turn would call GetErrors on each grandchild.
Now I need to validate different constraints for different operations, for example
Some constraints should always be checked because they are invariant
Some constraints should be checked when I want to perform operation X on the root.
Some additional constraints might be checked when performing operation Y.
I have considered adding a "Reason" parameter to the GetErrors method but for a reason I can't quite put my finger on this doesn't feel right. I have also considered creating a visitor and having a concrete implementation to validate for OperationX and another for OperationY but dislike this because some of the constraint checks would be required for multiple operations but not all of them (e.g. a Date is required for OperationX+OperationY but not OperationZ) and I wouldn't like to have to duplicate the code which checks.
Any suggestions would be appreciated.
You have an insulation problem here, as your classes are in charge of doing their own validation, yet the nature of that validation depends on the type of operation you're doing. This means the classes need to know about the kinds of operations that can be performed on them, which creates a fairly tight coupling between the classes and the operations that use them.
One possible design is to create a parallel set of classes like this:
public interface IValidate<T>
{
IEnumerable<ValidationError> GetErrors(T instance, string path);
}
public sealed class InvariantEntityValidator : IValidate<Entity>
{
public IEnumerable<ValidationError> GetErrors(Entity entity, string path)
{
//Do simple (invariant) validation...
}
}
public sealed class ComplexEntityValidator : IValidate<Entity>
{
public IEnumerable<ValidationError> GetErrors(Entity entity, string path)
{
var validator = new InvariantEntityValidator();
foreach (var error in validator.GetErrors(entity, path))
yield return error;
//Do additional validation for this complex case
}
}
You'll still need to resolve how you want to associate the validation classes with the various classes being validated. It sounds like this should occur at the level of the operations somehow, as this is where you know what type of validation needs to occur. It's difficult to say without a better understanding of your architecture.
I would do a kind of attribute-based validation:
public class Entity
{
[Required, MaxStringLength(50)]
public string Property1 { get; set; }
[Between(5, 20)]
public int Property2 { get; set; }
[ValidateAlways, Between(0, 5)]
public int SomeOtherProperty { get; set; }
[Requires("Property1, Property2")]
public void OperationX()
{
}
}
Each property which is passed to the Requires-attribute needs to be valid to perform the operation.
The properties which have the ValidateAlways-attribute, must be valid always - no matter what operation.
In my pseudo-code Property1, Property2 and SomeOtherProperty must be valid to execute OperationX.
Of course you have to add an option to the Requires-attribute to check validation attributes on a child, too. But I'm not able to suggest how to do that without seeing some example code.
Maybe something like that:
[Requires("Property1, Property2, Child2: Property3")]
If needed you can also reach strongly typed property pointers with lambda expressions instead of strings (Example).
I would suggest using the Fluent Validation For .Net library. This library allows you to setup validators pretty easily and flexibly, and if you need different validations for different operations you can use the one that applies for that specific operation (and change them out) very easily.
I've used Sptring.NET's validation engine for exactly the same reason - It allows you to use Conditional Validators. You just define rules - what validation to apply and under what conditions and Spring does the rest. The good thing is that your business logic is no longer polluted by interfaces for validation
You can find more information in documentation at springframework.net I will just copy the sample for the their doc to show how it looks like:
<v:condition test="StartingFrom.Date >= DateTime.Today" when="StartingFrom.Date != DateTime.MinValue">
<v:message id="error.departureDate.inThePast" providers="departureDateErrors, validationSummary"/>
</v:condition>
In this example the StartingFrom property of the Trip object is compared to see if it is later than the current date, i.e. DateTime but only when the date has been set (the initial value of StartingFrom.Date was set to DateTime.MinValue).
The condition validator could be considered "the mother of all validators". You can use it to achieve almost anything that can be achieved by using other validator types, but in some cases the test expression might be very complex, which is why you should use more specific validator type if possible. However, condition validator is still your best bet if you need to check whether particular value belongs to a particular range, or perform a similar test, as those conditions are fairly easy to write.
If you're using .Net 4.0, you can use Code Contracts to control some of this.
Try to read this article from top to bottom, I've gained quite a few ideas from this.
http://codebetter.com/jeremymiller/2007/06/13/build-your-own-cab-part-9-domain-centric-validation-with-the-notification-pattern/
It is attribute based domain validation with a Notification that wraps those validations up to higher layers.
I would separate the variant validation logic out, perhaps with a Visitor as you mentioned. By separating the validation from the classes, you will be keeping your operations separate from your data, and that can really help to keep things clean.
Think about it this way too -- if you mix-in your validation and operations with your data classes, think of what are things going to look like a year from now, when you are doing an enhancement and you need to add a new operation. If each operation's validation rules and operation logic are separate, it's largely just an "add" -- you create a new operation, and a new validation visitor to go with it. On the other hand, if you have to go back and touch alot of "if operation == x" logic in each of your data classes, then you have some added risk for regression bugs/etc.
I rely on proven validation strategy which has implemented in .net framework in 'System.ComponentModel.DataAnnotations Namespace' and for example used in ASP.NET MVC.
This one provides unobtrusive way to apply validation rules (using attributes or implementing IValidatableObject) and facilities to validate rules.
Scott Allen described this way in great article 'Manual Validation with Data Annotations'.
if you want to apply validation attributes on interface then look at MetadataTypeAttribute
to get better understanding how it works look at MS source code
I'm new to the .NET world having come from C++ and I'm trying to better understand properties. I noticed in the .NET framework Microsoft uses properties all over the place. Is there an advantage for using properties rather than creating get/set methods? Is there a general guideline (as well as naming convention) for when one should use properties?
It is pure syntactic sugar. On the back end, it is compiled into plain get and set methods.
Use it because of convention, and that it looks nicer.
Some guidelines are that when it has a high risk of throwing Exceptions or going wrong, don't use properties but explicit getters/setters. But generally even then they are used.
Properties are get/set methods; simply, it formalises them into a single concept (for read and write), allowing (for example) metadata against the property, rather than individual members. For example:
[XmlAttribute("foo")]
public string Name {get;set;}
This is a get/set pair of methods, but the additional metadata applies to both. It also, IMO, simply makes it easier to use:
someObj.Name = "Fred"; // clearly a "set"
DateTime dob = someObj.DateOfBirth; // clearly a "get"
We haven't duplicated the fact that we're doing a get/set.
Another nice thing is that it allows simple two-way data-binding against the property ("Name" above), without relying on any magic patterns (except those guaranteed by the compiler).
There is an entire book dedicated to answering these sorts of questions: Framework Design Guidelines from Addison-Wesley. See section 5.1.3 for advice on when to choose a property vs a method.
Much of the content of this book is available on MSDN as well, but I find it handy to have it on my desk.
Consider reading Choosing Between Properties and Methods. It has a lot of information on .NET design guidelines.
properties are get/set methods
Properties are set and get methods as people around here have explained, but the idea of having them is making those methods the only ones playing with the private values (for instance, to handle validations).
The whole other logic should be done against the properties, but it's always easier mentally to work with something you can handle as a value on the left and right side of operations (properties) and not having to even think it is a method.
I personally think that's the main idea behind properties.
I always think that properties are the nouns of a class, where as methods are the verbs...
First of all, the naming convention is: use PascalCase for the property name, just like with methods. Also, properties should not contain very complex operations. These should be done kept in methods.
In OOP, you would describe an object as having attributes and functionality. You do that when designing a class. Consider designing a car. Examples for functionality could be the ability to move somewhere or activate the wipers. Within your class, these would be methods. An attribute would be the number of passengers within the car at a given moment. Without properties, you would have two ways to implement the attribute:
Make a variable public:
// class Car
public int passengerCount = 4;
// calling code
int count = myCar.passengerCount;
This has several problems. First of all, it is not really an attribute of the vehicle. You have to update the value from inside the Car class to have it represent the vehicles true state. Second, the variable is public and could also be written to.
The second variant is one widley used, e. g. in Java, where you do not have properties like in c#:
Use a method to encapsulate the value and maybe perform a few operations first.
// class Car
public int GetPassengerCount()
{
// perform some operation
int result = CountAllPassengers();
// return the result
return result;
}
// calling code
int count = myCar.GetPassengerCount();
This way you manage to get around the problems with a public variable. By asking for the number of passengers, you can be sure to get the most recent result since you recount before answering. Also, you cannot change the value since the method does not allow it. The problem is, though, that you actually wanted the amount of passengers to be an attribute, not a function of your car.
The second approach is not necessarily wrong, it just does not read quite right. That's why some languages include ways of making attributes look like variables, even though they work like methods behind the scenes. Actionscript for example also includes syntax to define methods that will be accessed in a variable-style from within the calling code.
Keep in mind that this also brings responsibility. The calling user will expect it to behave like an attribute, not a function. so if just asking a car how many passengers it has takes 20 seconds to load, then you probably should pack that in a real method, since the caller will expect functions to take longer than accessing an attribute.
EDIT:
I almost forgot to mention this: The ability to actually perform certain checks before letting a variable be set. By just using a public variable, you could basically write anything into it. The setter method or property give you a chance to check it before actually saving it.
Properties simply save you some time from writing the boilerplate that goes along with get/set methods.
That being said, a lot of .NET stuff handles properties differently- for example, a Grid will automatically display properties but won't display a function that does the equivalent.
This is handy, because you can make get/set methods for things that you don't want displayed, and properties for those you do want displayed.
The compiler actually emits get_MyProperty and set_MyProperty methods for each property you define.
Although it is not a hard and fast rule and, as others have pointed out, Properties are implemented as Get/Set pairs 'behind the scenes' - typically Properties surface encapsulated/protected state data whereas Methods (aka Procedures or Functions) do work and yield the result of that work.
As such Methods will take often arguments that they might merely consume but also may return in an altered state or may produce a new object or value as a result of the work done.
Generally speaking - if you need a way of controlling access to data or state then Properties allow the implementation that access in a defined, validatable and optimised way (allowing access restriction, range & error-checking, creation of backing-store on demand and a way of avoiding redundant setting calls).
In contrast, methods transform state and give rise to new values internally and externally without necessarily repeatable results.
Certainly if you find yourself writing procedural or transformative code in a property, you are probably really writing a method.
Also note that properties are available via reflection. While methods are, too, properties represent "something interesting" about the object. If you are trying to display a grid of properties of an object-- say, something like the Visual Studio form designer-- then you can use reflection to query the properties of a class, iterate through each property, and interrogate the object for its value.
Think of it this way, Properties encapsulate your fields (commoningly marked private) while at the same time provides your fellow developers to either set or get the field value. You can even perform routine validation in the property's set method should you desire.
Properties are not just syntactic sugar - they are important if you need to create object-relational mappings (Linq2Sql or Linq2Entities), because they behave just like variables while it is possible to hide the implementation details of the object-relational mapping (persistance). It is also possible to validate a value being assigned to it in the getter of the property and protect it against assigning unwanted values.
You can't do this with the same elegance with methods. I think it is best to demonstrate this with a practical example.
In one of his articles, Scott Gu creates classes which are mapped to the Northwind database using the "code first" approach. One short example taken from Scott's blog (with a little modification, the full article can be read at Scott Gu's blog here):
public class Product
{
[Key]
public int ProductID { get; set; }
public string ProductName { get; set; }
public Decimal? UnitPrice { get; set; }
public bool Discontinued { get; set; }
public virtual Category category { get; set; }
}
// class Category omitted in this example
public class Northwind : DbContext
{
public DbSet<Product> Products { get; set; }
public DbSet<Category> Categories { get; set; }
}
You can use entity sets Products, Categories and the related classes Product and Category just as if they were normal objects containing variables: You can read and write them and they behave just like normal variables. But you can also use them in Linq queries, persist them (store them in the database and retrieve them).
Note also how easy it is to use annotations (C# attributes) to define the primary key (in this example ProductID is the primary key for Product).
While the properties are used to define a representation of the data stored in the database, there are some methods defined in the entity set class which control the persistence: For example, the method Remove() marks a given entity as deleted, while Add() adds a given entity, SaveChanges() makes the changes permanent. You can consider the methods as actions (i.e. you control what you want to do with the data).
Finally I give you an example how naturally you can use those classes:
// instantiate the database as object
var nw = new NorthWind();
// select product
var product = nw.Products.Single(p => p.ProductName == "Chai");
// 1. modify the price
product.UnitPrice = 2.33M;
// 2. store a new category
var c = new Category();
c.Category = "Example category";
c.Description = "Show how to persist data";
nw.Categories.Add(c);
// Save changes (1. and 2.) to the Northwind database
nw.SaveChanges();