Learning C# and OOP, Properties, Part 1

Richard Baldwin explains properties in C# and provides a comparison between C# properties and Java properties.  He also explains the importance of properties with respect to reflection and introspection.

Published:  October 29, 2002
By Richard G. Baldwin

C# Programming Notes # 106a


Preface

This lesson is part of a miniseries designed to teach you how to write object-oriented programs using C#.  This miniseries will describe and discuss the necessary and significant aspects of object-oriented programming (OOP) using C#.

The first lesson in the miniseries was entitled Learning C# and OOP: Getting Started, Objects and Encapsulation.  The previous lesson was entitled Learning C# and OOP, Classes.

Comparisons with Java

The miniseries will also make comparisons between C# and Java with respect to both syntax and OOP concepts.  I will emphasize the similarities between these two programming languages, which are likely to dominate the programming world in the foreseeable future.  By studying these lessons and learning about OOP using C#, you will also be learning quite a lot about OOP using Java.

Relatively high level

I will provide the information in a high-level format, devoid of any prerequisite requirement to know C# syntax.  In those cases where an understanding of C# syntax is required, I will provide the necessary syntax information in the form of sidebars and sample programs.

Therefore, if you have a general understanding of computer programming, you should be able to read and understand the lessons in this miniseries, even if you don't have a background in object-oriented programming, or a background in the C# programming language.

Viewing tip

You may find it useful to open another copy of this lesson in a separate browser window.  That will make it easier for you to scroll back and forth among the different listings while you are reading about them.

Supplementary material

I recommend that you also study the other lessons in my extensive collection of online programming tutorials.  You will find a consolidated index of my online tutorial lessons at www.DickBaldwin.com.

Preview

First of two parts

This is the first part of a two-part lesson that will concentrate on properties in C# and a comparison of C# properties with Java properties.  A sample C# program is provided to illustrate C# properties.  A sample Java program is also provided to illustrate the similarity of properties between C# and Java.

Methods and fields

You will see that C# properties act like methods to the creator of the class but look like public fields to clients of the class.  As a result, public fields and properties are indistinguishable to readers of the C# code who don't have ready access to documentation on the class.

You will also see that Java properties look like methods to clients of the class, and it is impossible to confuse properties with public fields in Java.

Properties are used for essentially the same purpose in both languages.

Properties support data hiding

Both C# properties and Java properties provide the data hiding generally required by good object-oriented design.  However, properties are not a prerequisite for data hiding.  Data hiding can be easily accomplished in either C# or Java in the absence of properties.

Reflection and introspection

Perhaps the most important characteristic of properties has to do with reflection and introspection.  This is a process whereby one object can discover and manipulate the properties belonging to another object, instantiated from a class that may not have existed when the class of the first object was defined.  Reflection and introspection will be discussed in detail in the second part of this two-part lesson.

Bound properties and constrained properties

Another important characteristic of properties has to do with bound properties and constrained properties.  This is a process by which an object can be automatically notified when the value of a bound or constrained property belonging to another object changes.  A brief discussion of bound and constrained properties will be provided in the second part of this lesson.

C# and Java properties are very similar

Properties are so similar between C# and Java that if you understand properties in either language, you should have no difficulty understanding properties in both languages.
 

Discussion and Sample Code

What is a property?

In C#, a property is created by including a special block of code in a class definition.  The syntax of this special block of code is unlike anything else in C#.

In Java, a property is created by including one or both of a pair of set and get methods meeting a certain format specification in a class definition.

By the time you finish studying the two parts of this lesson, you should know what properties are, and you should know how to create and use them in both C# and Java.

What others have to say about properties

Let's begin with what others have to say about properties.  Here is what Microsoft has to say in the documentation for the PropertyInfo class:

"Properties are logically the same as fields. A property is a named aspect of an object's state whose value is typically accessible through get and set accessors. Properties may be read-only, in which case a set routine is not supported."

Programming C# by Jesse Liberty

Here's what Jesse Liberty has to say about properties in his O'Reilly book entitled Programming C#.

"... properties ... act like methods to the creator of the class but look like fields to clients of the class.

Properties allow clients to access class state as if they were accessing member fields directly, while actually implementing that access through a class method.

Properties provide a simple interface to the client, appearing to be a member variable.  They are implemented as methods, however, providing the data hiding required by good object-oriented design."

As you will see later, this description is true for C# properties, but is not true for properties in general.

C# In A Nutshell

Here is what the authors of C# In A Nutshell from O'Reilly have to say on the matter:

"Properties can be characterized as object-oriented fields.  Properties promote encapsulation by allowing a class or struct to control access to its data, and by hiding the internal representation of the data."

This is true, of course, but there seems to be something missing.  The same data-hiding benefits can be, and have been, achieved by C++ programmers for years, using simple accessor methods.  Data hiding is made possible by the availability of access modifiers for class members.  Typically data hiding is achieved by providing public methods for accessing private instance variables.  While properties generally use this same scheme, properties are not a prerequisite for data hiding.

C# Primer, A Practical Approach

Here is what Stanley Lippman has to say in C# Primer, A Practical Approach from Addison-Wesley.

"A property typically is a public class member providing read and possibly write access to a private data member of the class.  We define a property by specifying an access level, type, and property name."

What does Dick Baldwin have to say on the matter?

In my opinion, all of the above descriptions have missed the mark in terms of what properties are really all about.  If the benefits of properties were limited to the above descriptions, it would not have been worth the effort for Microsoft to develop a new and cryptic syntax for properties.  Similarly, it would not have been worth the effort for Sun to develop design patterns for properties.

The real importance of properties is not based on making methods look like fields.  Also, the importance is not based on data hiding.  Rather, the real importance of properties has to do with reflection and introspection, which I will discuss in detail in the second part of this two-part lesson.

(Another important aspect of Java properties has to do with bound properties and constrained properties, which I will also discuss in the second part of this lesson.)

Fields or methods?

Liberty's statement that "properties, ... act like methods to the creator of the class but look like fields to clients of the class" is true for C#, but is not true in general.

In my opinion, whether properties look like fields or look like methods is immaterial to the experienced programmer.  I can't imagine that an experienced OOP programmer would care one way or the other.

Java has provided the benefits of properties in its JavaBeans Component technology for several years, and Java properties do not look like fields to clients of the class.  Rather, they look like simple method invocations to clients of the class.  In the six or more years that I have been involved in Java, I have yet to hear anyone complain that Java properties don't look like fields.

Not a prerequisite for data hiding

As mentioned earlier, the availability of properties is not a prerequisite for the "data hiding required by good object-oriented design."  Data hiding has been easily accomplished for many years in C++ using private instance variables and public accessor methods with no concept of properties being involved.

My description of a property

The following paragraphs contain my description of a property.  This description is based on practical considerations.  For the most part, I will describe the things that must be true for a property to exist, and more importantly, to be really useful.

Name, type, and value

First, a property must have a name, a type, and a value, and possibly some other attributes as well, (such as being read only or read/write).

(In the next lesson, I will discuss indexed properties that have more than one value.)

Same name and type, but different value

A property belongs to an object.  Every object instantiated from the same class will have the same set of properties.  The properties belonging to all the objects instantiated from the same class will have the same names and types, but won't necessarily have the same values from one object to the next.

Where is the value stored?

The value of a property is probably most commonly stored in an instance variable belonging to the object, but that is not a requirement.  The value could be stored in a database, or a disk file, or elsewhere, or could be computed on-the-fly when requested.

The state of the object

The value of a property generally contributes to the state of the object to which it belongs, and when the value of the property changes, the state of the object changes accordingly.

(When the state of an object changes due to a change in a bound property value, other interested objects can be automatically notified of that change of state.)

Standardization is required

To be really useful, the access methodology for a property must be predefined and standardized within a given programming language.  However, the access methodology need not be the same from one language to the next.  As mentioned earlier, C# accesses properties as fields, while Java accesses properties as methods.

The real importance of properties

It must be possible for executing code to learn everything there is to know about the properties belonging to a (previously unknown) object at runtime, and to be able to access those properties for reading and writing at runtime.  This must be possible even though the author of the executing code had no knowledge of the unknown object's class when the code was originally written.

(In C#, this is referred to as reflection.  In Java, it is referred to as introspection based on low-level reflection.)

Because .NET is language-neutral, this capability must exist across all languages supported by .NET, even if the language used to define the class and its properties is different from the language used to instantiate objects from the class.

A real-world example

Let me describe a real-world example of what I mean.  Ever since the introduction of Visual Basic several years ago, software developers have been interested in using standard software components to develop software.  Using software components to develop software is similar to using electronic components to manufacture electronic devices.

The great promise of using standard software components to develop software is that it can reduce the cost of software development in the same way that the use of standard electronic components has reduced the manufacturing cost of electronic devices such as computers.

A toolkit full of software components

In this style of programming, the programmer has access to a toolkit full of software components, and a builder tool that can be used to wire those software components together in order to produce a software application.

A sophisticated computer program

The builder tool itself is a very sophisticated and complex computer program.  In order for the builder tool to wire software components together, according to the wishes of the programmer, the builder tool must be able to extract the following information (as a minimum) from each software component that is installed in the toolkit:

  • Properties
  • Events
  • Methods

Components need to communicate

For example, when two components are wired together, one component may need to access, and possibly modify, property values belonging to the other component.  This is only possible if the builder tool can discover everything that it needs to know about the properties of every component in the toolkit.  (The builder tool is unable to read the documentation for a software component the way you and I do.)

Property editors

Even before getting to the point where one component needs to access the properties belonging to another component, the builder tool itself usually needs to discover and access the properties of every component being used to develop an application.

Most builder tools provide a property editor as a graphical user interface (GUI). The property editor makes it possible for the programmer to set initial property values on every software component so that the program being developed will start running with all of its component objects in the correct state.  For example, the programmer will normally want to set the location, height, width, text, and color of each visual button so that it will be in the correct location with the correct size, text, and color when the program starts running.

As distinguished from data hiding

In my opinion, the ability to accomplish this under software control is what separates properties from ordinary data hiding that we have been practicing for many years.

Should properties look like fields or methods?

The ability to accomplish the discovery of properties at runtime has nothing to do with whether the property looks like a field or looks like a method.  It has been done successfully both ways.  Some programmers may prefer one approach to the other, but in reality, the difference is trivial.  To an experienced programmer, the difference in programming effort between the two approaches is negligible.

Self-documenting code

In my opinion, however, the approach where the property looks like a method is the more self-documenting of the two.  This approach produces code that is easier to read and understand by interested third parties who don't have ready access to the class documentation.

We have been striving for years to develop better self-documenting programming styles.  Making properties look like fields instead of methods is a step backwards in my opinion.  However, from a technical viewpoint, it can obviously be done either way.

What really matters is ...

What really matters is that the mechanism for accessing properties be predefined and standardized so that code can discover and manipulate the properties at runtime.

Common at the MSIL level

It is also a requirement that regardless of the programming syntax used by the different languages supported by .NET, they must all compile to the same result at the Microsoft Intermediate Language (MSIL) level.

(Interestingly, according to C# In A Nutshell, even though the property programming syntax at the source code level used by C# is radically different from that used by Java, the MSIL representation produced by C# looks like the Java source code representation.)

C# and Java approach standardization in different ways, and they both seem to work very well.  Even though the standardization approach is different between the two languages, the underlying concepts being implemented are very similar.

The C# approach to standardization

The C# approach uses a special source-code syntax to create a property.  You will see an example of this syntax in the sample program to be discussed later.  As far as I know, this special syntax must be used in all cases where you need to create a property in C#.

The Java approach to standardization

Java allows for two different approaches.  The simplest Java approach makes use of JavaBeans Design Patterns, which are nothing more than a set of well-defined naming conventions.  Using this approach, you can create a property in Java by causing the signatures of a pair of set and get methods to adhere to the design pattern specifications.  You will also see an example of this approach in the programs to be discussed later.

The other approach allowed by Java involves considerably more work.  With this approach, you must define a companion or helper class that implements a rather complex interface named BeanInfo.  An object instantiated from this helper class can be queried to discover the properties belonging to objects of the class that it is designed to help.

You won't see an example of this approach in this lesson.  If you would like to learn more about this approach, see my tutorial lesson entitled JavaServer Pages and JavaBean Components, Part III(In addition to providing additional information about this approach, this lesson also provides an interesting example of the use of the discovery process.)

It's time to look at some code

I'm going to show you a C# program that illustrates properties from three different viewpoints:

  • The viewpoint of the developer of the class that defines properties.
  • The viewpoint of the user of the class to simply set and get property values.
  • The viewpoint of the sophisticated user of the class to discover and use properties at runtime.

The third viewpoint contains some powerful material, and the discussion of the third viewpoint will be deferred until the second part of this two-part lesson.  While you might find it complex, I hope that you will stick with it until you understand the concepts involved.

A comparable Java program

In addition, I'm going to show you a comparable Java program that accomplishes exactly the same thing.  I will compare the code between the two programs and discuss the similarities and the differences.  You will see that even at the complex level of the third viewpoint, the concepts, and even the syntax in the C# program is very similar to the Java program.

Explain in fragments

The complete C# program is shown in Listing C11, and the complete Java program is shown in Listing J8.  These two listings are near the end of the lesson.

In order to help you to focus specifically on important sections of code, I will explain the behavior of these programs in fragments.

A target class

The C# program consists of two classes.  The first class that I will discuss is named TargetClass.  This class defines some properties (as well as some other members), which are accessed by code in the Main method of the other class named Props01.

Listing C1 shows the beginning of the code for the definition of the class named TargetClass.  Here we are seeing things from the viewpoint of the developer of the class named TargetClass.
 
public class TargetClass{

  public string text;

Listing C1

A public instance variable

The class named TargetClass declares a public instance variable of type string named text.  There's nothing exciting about a public instance variable.  I included it for demonstration purposes only.  I will show that there is no discernible difference between accessing a public instance variable and accessing a property in C#.

Implementing data hiding the conventional way

Listing C2 shows a pair of set and get methods that accomplish data hiding for this C# program.

(The signatures of these two methods also satisfy the JavaBeans Design Pattern for property accessor methods.  If this were a Java program, the existence of these two methods would create a property named color.)

  private int colorData = 0;

  public void setColor(int data){
    //Validating code goes here
    colorData = data;
  }//end setColor

  public int getColor(){
    return colorData;
  }//end getColor

Listing C2

Not a property in C#

However, this is not a Java program.  It's a C# program.  The signatures of these two methods do not create a property in C#.  A different syntax is required to create a property in C#.  This will be confirmed in the second part of this two-part lesson when we write program code to discover the properties of an object of this class.

A C# property

C# uses the syntax shown in boldface in Listing C3 to create a property named height.

(If the code block following set is omitted, the property is a read-only property.)

  private int heightData;

  public int height{
    get{
      return heightData;
    }//end get

    set{
      //Validating code goes here
      heightData = value;
    }//end set
  }//end height property

Listing C3

There isn't much more for me to tell you about this syntax.  You will simply need to memorize it (pay particular attention to the number and location of the curly braces).

The property value

In this case, the property value is stored in the instance variable named heightData.  However, that is not a requirement.  The code could be written to store the property value in a database, in a disk file, or in any other location accessible by the code in the object.

The name and type of the property

The name and type of the property is established by the line of code that reads

public int height{

In this case, the property is named height and it is type int.

The get method

Although they don't look like methods, this code effectively contains two methods named get and set.

Whenever the using code references the property name in a fetching sense, the code in the get block is executed.  This block must contain a return statement to return a value of the specified type.  The get block could also contain any other code that you might want to have executed in conjunction with such a fetch operation.  An example of a fetch operation is highlighted in boldface below, where obj is a reference to an object instantiated from this class.

Console.WriteLine("height: " + obj.height);

The set method and the value parameter

Whenever the using code references the property name in a storage sense (as the left operand of an assignment operator, for example), the code in the set block is executed.

The value to be stored (the right operand of the assignment operator, for example) is passed to the set code as a hidden parameter named value.  The name of this hidden parameter never changes.  The code in the set block must save the value of the hidden parameter named value in an appropriate location if it is to be successfully returned later.

Additional code

You can place any code that you might want to have executed in conjunction with such a set operation in the set block.  Data validation code is particularly appropriate here.

An example of such a storage operation is shown below where obj is a reference to an object instantiated from this class.

obj.height = 20;

In this case, the hidden parameter named value will have an int value of 20.

Another property named width

Listing C4 shows code that defines another property of type int named width.  This code uses the same syntax as that used for the property named height.
 
  private int widthData;

  public int width{
    get{
      return widthData;
    }//end get
    set{
      //Validating code goes here
      widthData = value;
    }//end set
  }//end width property

Listing C4

This is the end of the class definition for the class named TargetClass.

An object of type TargetClass

An object instantiated from the class named TargetClass contains:

  • One public instance variable of type string named text.  Data hiding is not accomplished with respect to this instance variable.
  • One private instance variable named colorData protected by accessor methods named setColor and getColor.  Data hiding is accomplished with respect to this instance variable without the use of properties.  (The use of properties is not necessary to accomplish data hiding.)
  • Two properties of type int named height and width.  Data hiding is accomplished here also.

Switching viewpoints

Now its time to switch to the viewpoint of the user of the class named TargetClass.  This user already knows the names and types of the properties and has no interest in discovering properties at runtime.

The Main method

Listing C5 shows the beginning of the class named Props01 and the beginning of the Main method in that class.

This code begins by instantiating and saving a reference to a new object of the class named TargetClass discussed above.  The reference is saved in the reference variable named obj.  The reference to this object will be used to access the public instance variable, the hidden data, and the properties of this object.

(The reference will also be used in the second part of this two-part lesson, along with reflection, to discover the properties belonging to the object at runtime.)

public class Props01{
  static TargetClass obj;
  
  public static void Main(){
    obj = new TargetClass();

Listing C5

Access the public instance variable

The code in Listing C6 uses the object's reference to directly store the string "Quit" in the public instance variable named text.  Following this, the code uses the object's reference to directly get and display the value in the public instance variable named text.
 
    obj.text = "Quit";
    Console.WriteLine(
                  "text: " + obj.text);

Listing C6

Will compare with property access methodology

There is nothing particularly interesting about the code in Listing C6.  This code is presented here for later comparison with code that accesses the properties.  The code in Listing C6 produces the following output on the screen.

text: Quit

Accessing the hidden data

The code in Listing C7 uses the two accessor methods to first set a value in the private instance variable, and then to get and display that value.  Note that data hiding is fully supported here without the use of properties.
 
    obj.setColor(15);

    Console.WriteLine(
           "color: " + obj.getColor());

Listing C7

Listing C7 is a straightforward application of simple data hiding using accessor methods.  No special support of any kind is required to use this technique.  The code in Listing C7 produces the following output on the screen:

color: 15

Accessing a property

Now we are going to access a C# property in a simple non-discovery way.  This is shown in Listing C8.
 
    obj.height = 20;

Listing C8

The code in Listing C8 sets the value 20 in the property named height.

Appears to access a public field

Note that the syntax of this statement looks exactly like the syntax of the first statement in Listing C6 (except that the data type is different), which assigns a value directly to a public instance variable.  Without having access to the documentation for the class named TargetClass, it would not be possible for the reader of this code to know whether height is the name of a property or is the name of a public instance variable.

Not self-documenting code

This is what I meant earlier when I said that this approach to property access is not self-documenting.  For the experienced programmer, the first statement in Listing C7, which invokes a method, is no more challenging than the statement in Listing C8, which appears to access a public field.

I can't imagine why an experienced programmer would prefer for properties to look like public fields, given the significant loss in self-documentation that results from that design.  Other than the self-documentation aspect, however, it seems to me that this difference is a trivial syntax issue.

Display the property value.

Listing C9 gets and displays the value stored in the property named height.
 
    Console.WriteLine(
              "height: " + obj.height);

Listing C9

Again, this looks like the code is accessing a public field named height.  Without having access to the documentation for the class named TargetClass, the reader of the code would have no way of knowing any different.

The code in Listing C9 produces the following output on the computer screen:

height: 20

Accessing another property

Listing C10 first sets, and then gets and displays the value of the property named width.
 
    obj.width = 50;
    Console.WriteLine(
                "width: " + obj.width);

Listing C10

There's nothing new here.  The code in Listing C10 produces the following output on the computer screen:

width: 50

A comparable Java program

Now I'm going to show you a Java program that accomplishes exactly the same thing as the C# program discussed above.  As with the C# program, the Java program will illustrate properties from three significantly different viewpoints:

  • The viewpoint of the developer of the class that defines properties.
  • The viewpoint of the user of the class to simply set and get property values.
  • The viewpoint of the sophisticated user of the class to discover and use properties at runtime.

As was the case with the C# program, the third viewpoint contains some powerful material, and will be discussed in detail in the second part of this two-part lesson.  While you might find it somewhat complex, I hope that you will stick with it until you understand the concepts involved.

The most significant aspect of the third viewpoint will be the remarkable similarity between the C# code and the Java code, even at this complex level.

Explain in fragments

The complete Java program is shown in Listing J8 near the end of the lesson.  As usual, in order to help you to focus on important sections of code, I will explain the behavior of this program in fragments.

A target class

As was the case with the C# program, the Java program consists of two classes.  The first class that I will discuss is named TargetClass.  This class defines some properties, which are accessed by code in the main method of the other class named Props01.

Listing J1 shows the beginning of the definition of a Java class that mimics the behavior of the C# class shown in Listings C1 through C4.  Here we are seeing things from the viewpoint of the developer of the class named TargetClass.
 
class TargetClass 
               implements Serializable{

  public String text;

Listing J1

Serializable interface

This Java class implements the Serializable interface.  Without getting into the details, let me just say that this is required to cause the class to satisfy the JavaBeans Component specification, making it suitable for introspection.  (Introspection will be explained and illustrated in the second part of this two-part lesson.)

Class not declared public

Note that unlike the C# class in Listing C1, I didn't declare the Java class public.  Rather, by not declaring an access level, I caused this class to be package private by default.  This was done strictly for convenience.  In Java, every public class must be defined in a separate source code file.  I made this class package private to avoid the requirement to create and maintain separate source code files for each of the class definitions in the program. (Java access of package private is similar to internal access in C#.)

A public instance variable

As was the case with the C# class in Listing C1, this class definition begins with the declaration of a public instance variable.  This instance variable will be used later to illustrate that access to a property in Java has no resemblance to access to a public instance variable.  Therefore, it isn't possible to confuse the two.

A property named color

The Java code in Listing J2 is identical to the C# code in Listing C2.
 
  private int colorData = 0;

  public void setColor(int data){
    //Validating code goes here
    colorData = data;
  }//end setColor

  public int getColor(){
    return colorData;
  }//end getColor

Listing J2

As is the case in C#, the code in Listing J2 accomplishes data hiding by providing public accessor methods for a private instance variable.  Perhaps more important, the code in Listing J2 creates a Java property named color.

This is all that is required to create a property in Java.  No special and unusual source code syntax is required.  All that is required is to provide accessor methods that satisfy the JavaBeans Design Pattern for property accessor methods, and these two methods meet that requirement.

The name and type of the property

According to the JavaBeans Design Pattern for property accessor methods, the name of the Java property is the word following get or set in the name of the accessor methods, with the case of the first character flipped.  The type of the property is the same as the type of the single argument of the set method, which must match the return type of the get method.

The property value

For the code in Listing J2, the property value is stored in the instance variable named colorData.  However, as with C#, this is not a requirement.  The code could be written to store the property value in a database, in a disk file, or in any other location accessible by the code in the object.

Properties named height and width

The code in Listing J3 creates two more Java properties named height and width.
 
  private int heightData;

  public void setHeight(int data){
   //Validating code goes here
   heightData = data;
  }//end setHeight

  public int getHeight(){
    return heightData;
  }//end getHeight


  private int widthData;

  public void setWidth(int data){
   //Validating code goes here
   widthData = data;
  }//end setwidth

  public int getWidth(){
    return widthData;
  }//end getwidth
  
Listing J3

The code in Listing J3 is different from the C# code in Listings C3 and C4 used to create C# properties named height and width.  This is because Listings C3 and C4 used the special syntax required to create properties in C#.  In the end, however, the properties behave essentially the same way in both languages.

Listing J3 is also the end of the Java class definition for the class named TargetClass.

An object of type TargetClass

A Java object instantiated from the class named TargetClass contains:

  • One public instance variable of type string named text.  Data hiding is not accomplished with respect to this instance variable.
  • Three properties of type int named color, height, and width.  Because the property value is stored in a private instance variable, this code also accomplishes data hiding.

Switching viewpoints

Now its time to switch to the viewpoint of the user of the class named TargetClass.  This user knows the names and types of the properties and has no interest in discovering properties at runtime.

The main method

Listing J4 shows the beginning of the class named Props01 and the beginning of the main method for that class.  Except for the difference in the signature of the main method, (which I explained in an earlier lesson), the Java code in Listing J4 is identical to the C# code in Listing C5.
 
public class Props01{
  static TargetClass obj;
  
  public static void main(
                        String[] args){
    obj = new TargetClass();

Listing J4

The code in Listing J4 begins by instantiating and saving a reference to a new object of the class named TargetClass discussed above.  The reference is saved in the reference variable named obj.  The reference to this object will be used to access the public instance variable and the properties of this object.

(The reference will also be used in the second part of this two-part lesson, along with introspection, to discover the properties belonging to the object at runtime.)

Access the public instance variable

As was the case in the C# program, the code in Listing J5 uses the object's reference to directly store the string "Quit" in the public instance variable named text.  Following this, the code uses the object's reference to directly get and display the value in the public instance variable named text.

(Except for the different syntax required for console output, this code is identical to the C# code in Listing C6.)

    obj.text = "Quit";
    System.out.println(
                  "text: " + obj.text);

Listing J5

Will compare with property access methodology

There is nothing particularly interesting about the code in Listing J5.  This code is presented here for later comparison with code that accesses the properties.  The code in Listing J5 produces the following output on the screen.

text: Quit

Accessing the property named color

The code in Listing J6 uses the two property access methods to first set a value in the property named color, and then to get and display that value.  Note that data hiding is fully supported here.
 
    obj.setColor(15);

    System.out.println(
           "color: " + obj.getColor());

Listing J6

Again, except for the different syntax used for console output, the Java code in Listing J6 is identical to the C# code in Listing C7. The difference, however, is that this Java code involves setting and getting a property value, while that is not the case with the C# code.

The code in Listing J6 produces the following output on the screen:

color: 15

Syntax comparison

It is also important to note that this property access syntax bears no resemblance to the code in Listing J5, which accesses a public instance variable.  There is no chance of confusing public instance variables with properties in Java.  Thus, the syntax used for accessing properties in Java is more self-documenting than the syntax used for accessing properties in C#.

Accessing the properties named height and width

The code in Listing J7 uses the property access methods to first set, and then get and display the values in the properties named height and width.
 
    obj.setHeight(20);
    System.out.println("height: " + 
                      obj.getHeight());

    obj.setWidth(50);
    System.out.println("width: " + 
                       obj.getWidth());

Listing J7

Compare the bottom half of the code in Listing J7 (width property access) with the C# code in Listing C10 to see a direct comparison of the difference in property access mechanisms in C# and Java.  There's nothing new here, so I won't discuss it further.

The code in Listing J7 produces the following output on the computer screen:

height: 20
width: 50

Summary

Concentrate on properties

This lesson has concentrated on properties in C# and a comparison of C# properties with Java properties.  A sample C# program was provided to illustrate C# properties.  A sample Java program was also provided to illustrate the similarity of properties in C# and Java.

Methods and fields

C# properties act like methods to the creator of the class but look like public fields to clients of the class.  As a result, public fields and properties are indistinguishable to readers of the code who don't have ready access to documentation on the class.

Java properties look like methods to clients of the class.  As a result, it is impossible to confuse properties with public fields in Java.  In my opinion, Java properties are more self-documenting than C# properties.  Beyond this, however, properties are used for essentially the same purposes in both languages.

Properties support data hiding

Both C# properties and Java properties provide the data hiding generally required by good object-oriented design.  However, properties are not a prerequisite for data hiding.  Data hiding can be easily accomplished in C#, Java, or C++ in the absence of properties.

C# and Java properties are very similar

Properties are so similar in C# and Java that if you understand properties in either language, you should have no difficulty understanding properties in both languages.

What's Next?

Reflection and introspection

Perhaps the most important aspect of properties has to do with reflection and introspection.  This is a process whereby one object can discover and manipulate the properties belonging to another unknown object even though the author of the executing program had no knowledge of the unknown object's class when the executing program was originally written.

This will be discussed in detail in the second part of this two-part lesson.

Bound properties and constrained properties

Another important characteristic of properties has to do with bound properties and constrained properties.  This is a process by which an object can be registered to be automatically notified when the value of a bound or constrained property belonging to another object changes.

Indexed properties

In a future lesson, I will teach you about indexed properties.  These are properties containing multiple values, with each value being accessible through a numeric index.

Complete Program Listings

A complete listing of the C# program discussed in this lesson is shown in Listing C11.
 

/*File Props01.cs
Copyright 2002, R.G.Baldwin

This program is intended to explore and
explain the use of properties in C#.

Program tested using:
Microsoft (R) Visual C# .NET Compiler 
version 7.00.9466
for Microsoft (R) .NET Framework 
version 1.0.3705
Under Win2000 Version 5.0 SP 2

Program output is:
text: Quit
color: 15
height: 20
width: 50
Number of Public Properties: 2
Descriptions of Properties:
Name: height
Type: System.Int32
Value: 20
Name: width
Type: System.Int32
Value: 50
**************************************/
using System;
using System.Reflection;

public class TargetClass{
  //A public instance variable
  public string text;
  
  //This would be a property named
  // color in Java, but not in C#
  private int colorData = 0;
  public void setColor(int data){
    //Validating code goes here
    colorData = data;
  }//end setColor
  public int getColor(){
    return colorData;
  }//end getColor
  
  //This is a property named height
  private int heightData;
  public int height{
    get{
      return heightData;
    }//end get
    set{
      //Validating code goes here
      heightData = value;
    }//end set
  }//end height property

  //This is a property named width
  private int widthData;
  public int width{
    get{
      return widthData;
    }//end get
    set{
      //Validating code goes here
      widthData = value;
    }//end set
  }//end width property
  
}//end TargetClass
//===================================//

public class Props01{
  static TargetClass obj;
  
  public static void Main(){
    obj = new TargetClass();
    
    //Access a public instance 
    // variable
    obj.text = "Quit";
    Console.WriteLine(
                  "text: " + obj.text);
    
    //Invoke public accessor methods
    obj.setColor(15);
    Console.WriteLine(
           "color: " + obj.getColor());
    
    //Set and get a property
    obj.height = 20;
    Console.WriteLine(
              "height: " + obj.height);

    //Set and get another property
    obj.width = 50;
    Console.WriteLine(
                "width: " + obj.width);

    //Now do reflection to identify
    // properties of the object
    Type theType = obj.GetType();
    PropertyInfo[] propInfo = 
               theType.GetProperties();
    Console.WriteLine(
        "Number of Public Properties: "
                    + propInfo.Length);
    Console.WriteLine(
        "Descriptions of Properties:");
    // Display all the properties.
    DisplayPropertyInfo(propInfo);

  }//end Main
  
  public static void 
            DisplayPropertyInfo(
              PropertyInfo[] propInfo){
    for(int i=0;i<propInfo.Length;i++){
      PropertyInfo myPropInfo = 
                           propInfo[i];
      Console.WriteLine("Name: " + 
                      myPropInfo.Name);
      Console.WriteLine("Type: " + 
              myPropInfo.PropertyType);

      //Get and display the value
      MethodInfo readMethod = 
             myPropInfo.GetGetMethod();
      Console.WriteLine("Value: " +
          readMethod.Invoke(obj,null));

/*    Alternative approach for value
      Console.WriteLine("Value: " + 
        myPropInfo.GetValue(obj,null));
*/
      
    }//end for loop
  }//end DisplayPropertyInfo
  
}//end class Props01
//===================================//


Listing C11

A complete listing of the Java program discussed in this lesson is shown in Listing J8.
 
/*File Props01.java
Copyright 2002, R.G.Baldwin

This program is intended to explore and
explain the use of properties in Java,
and is designed for comparison with a
similar C# program.

Program tested using:
SDK 1.4.0 under Win2000 V5.0 SP2

Program output is:
text: Quit
color: 15
height: 20
width: 50
Number of Properties: 3
Descriptions of Properties:
Name: color
Type: int
Value: 15
Name: height
Type: int
Value: 20
Name: width
Type: int
Value: 50
**************************************/
import java.beans.*;
import java.lang.reflect.*;
import java.io.*;

//This class is not declared public in
// order to avoid the rqmt for separate
// files
class TargetClass 
               implements Serializable{
  //A public instance variable
  public String text;
  
  //This is a property named color
  private int colorData = 0;
  public void setColor(int data){
    //Validating code goes here
    colorData = data;
  }//end setColor
  public int getColor(){
    return colorData;
  }//end getColor
  
  //This is a property named height
  private int heightData;
  public void setHeight(int data){
   //Validating code goes here
   heightData = data;
  }//end setHeight
  public int getHeight(){
    return heightData;
  }//end getHeight
  
  //This is a property named width
  private int widthData;
  public void setWidth(int data){
   //Validating code goes here
   widthData = data;
  }//end setwidth
  public int getWidth(){
    return widthData;
  }//end getwidth
  
}//end TargetClass
//===================================//

public class Props01{
  static TargetClass obj;
  
  public static void main(
                        String[] args){
    obj = new TargetClass();
    
    //Access a public instance 
    // variable
    obj.text = "Quit";
    System.out.println(
                  "text: " + obj.text);
    
    //Invoke property methods
    obj.setColor(15);
    System.out.println(
           "color: " + obj.getColor());
    
    obj.setHeight(20);
    System.out.println("height: " + 
                      obj.getHeight());

    obj.setWidth(50);
    System.out.println("width: " + 
                       obj.getWidth());

    //Now do reflection and 
    // introspection to identify
    // properties of the object
    Class theType = obj.getClass();

    try{
      BeanInfo beanInfo = 
      Introspector.getBeanInfo(
                    theType,theType.
                      getSuperclass());

    
      PropertyDescriptor[] propInfo = 
            beanInfo.
              getPropertyDescriptors();

      System.out.println(
               "Number of Properties: "
                    + propInfo.length);
      System.out.println(
        "Descriptions of Properties:");
      // Display all the properties.
      displayPropertyInfo(propInfo);
    }catch(IntrospectionException e){
                  e.printStackTrace();}

  }//end Main
  
  public static void 
      displayPropertyInfo(
        PropertyDescriptor[] propInfo){
    for(int i=0;i<propInfo.length;i++){
      PropertyDescriptor myPropInfo = 
                           propInfo[i];
      System.out.println("Name: " + 
                 myPropInfo.getName());

      System.out.println("Type: " +
         myPropInfo.getPropertyType());

      //Get and display the value
      Method readMethod = 
            myPropInfo.getReadMethod();
      try{
        System.out.println("Value: " + 
          readMethod.invoke(obj,null));
      }catch(Exception e){
        e.printStackTrace();}
    }//end for loop
  }//end displayPropertyInfo
  
}//end class Props01

Listing J8

Review Questions

The second part of this two-part lesson will contain review questions, answers, and explanations for both parts of the lesson.



Richard Baldwin is a college professor (at Austin Community College in Austin, Texas) and private consultant whose primary focus is a combination of Java, C#, and XML. In addition to the many platform and/or language independent benefits of Java and C# applications, he believes that a combination of Java, C#, and XML will become the primary driving force in the delivery of structured information on the Web.

Richard has participated in numerous consulting projects and he frequently provides onsite training at the high-tech companies located in and around Austin, Texas.  He is the author of Baldwin's Programming Tutorials, which has gained a worldwide following among experienced and aspiring programmers. He has also published articles in JavaPro magazine.

Richard holds an MSEE degree from Southern Methodist University and has many years of experience in the application of computer technology to real-world problems.



Copyright 2002, Richard G. Baldwin.  Reproduction in whole or in part in any form or medium without express written permission from Richard Baldwin is prohibited.

baldwin@DickBaldwin.com

-end-


© 1996, 1997, 1998, 1999, 2000, 2001, 2002 Richard G. Baldwin