Showing posts with label c#. Show all posts
Showing posts with label c#. Show all posts

Sunday, February 24, 2008

An odd case of senioritis

In high school, I used to wonder how people managed to get senioritis—the mythical disease contracted during graduation year with the symptoms of being really, really lazy. I was actually the opposite way; senior year is probably when I worked the hardest, since I was taking calculus classes at Purdue, as well as AP French and Physics C (for both kinematics and e&m). Now that I'm on my way out of college, however, things appear to have changed. Not only do I procrastinate madly on my homework, which has resulted in all-nighters for both of my parallel computing assignments, I've also picked up a habit of not going to a significant percentage of my numerical methods class. I don't think it will ever become a serious problem, though it makes me feel like a serious slacker.

Fortunately, this whole slacking business seems to have an upside. Since neither of my classes has a "real" programming component (yet), I've been doing more extra-curricular programming than I thought I would have time for. RITA has made decent progress, and some people use it for monitoring purposes even though it's technically not production ready. The key items that still need attending to include cleaning up the terrible mess I've made out of the code, as well as implementing a few more options. That aside, I was able to code up some other needed features, such as syncing to ResNet's traffic stats on the hour (which can still be tweaked some, I suppose), displaying the traffic graph, and creating a task tray icon with gauges to determine how close you are to the bandwidth limit. The tray icon was probably the most tedious, but it ended up being the most interesting. At first I had static icons set to display at low, medium, and high levels. The granularity of that is highly dissatisfactory and the icons weren't even displaying properly, for some reason, so I ditched that. In the end, I just dynamically drew the icons as necessary. This saved me the trouble of drawing 196 icons and calculating 14 different colors to use; even though the middle area turns to an ugly brown color, I'm still happy that it actually works.

The other project I've been working on starts with Ragel, which is a state machine compiler. I was interested in seeing how efficient an IRC library parser, which is really quite simple, could be in C#. SmartIrc4Net is one obvious benchmark to compare against; the single regular expression in Parse::IRC is another. Ragel is supposed to be really fast, so I wanted to try it out. The problem is that Ragel only supported Java, not C#, so my first task was to implement C# output for Ragel. This didn't turn out to be very hard; instead, it was mostly fixing errors that surfaced because of differences between C and C#, such as type safety rules.

Implementing a simple parser for IRC is not so hard; the syntax is pretty easy to break down. By "simple" I essentially mean that it's like a single regular expression. I was able to implement it at the end of the week, though I had trouble getting Ragel's scanners to work. Instead of using scanners, I used one of Ragel's cool features, embeddable actions, to mark tokens on transition enters and exits. I finished my first "benchmark" comparison against the giant Parse::IRC regular expression as well, after sticking it into a C# Regex object. The benchmark was simply to parse a few IRC commands a million times; as it turns out, Ragel is about 33% faster than a compiled Regex object in this measurement. It's kind of fun to suddenly start worrying a lot about efficiency, even though parsing is probably a small task compared to, well, what the rest of an IRC client would do. There is still more to be done with the Ragel parser, before I start trying to actually incorporate it into a library, though. More on that later, maybe.

Along the way, I got kind of annoyed at switching between Vim, a DOS prompt, and Visual Studio. Lucky for me, I discovered custom tools, which are basically processors that take a file and spit out code in a certain language. I implemented a custom tool processor for Ragel yesterday, so now I can use Visual Studio for everything. Using cmd.exe gets pretty annoying, especially when you're used to bash.

There's still much that could be done—I haven't done anything with Django this semester, which is kind of sad, but I guess you have to prioritize at some point. Hopefully this motivation sticks around long enough for me to eventually get to more web programming. Even though I've always been more of a desktop/non-web programmer myself, Django is a pretty cool piece (pieces?) of software, and I guess the web is the future and all that jazz.

Saturday, February 09, 2008

On C# and properties (continued)

Awhile ago, I posted about a problem that I started coming across when I took software engineering with C#'s properties. Even though it was a great improvement over Java's get/set methods, there are still problems to be had (you can read the article here.

Interestingly enough, the release of C# 3.0 has fixed this problem, and in a much better way than I had thought of. I discovered this while working on RITA in Visual Studio 2008, whose property snippets (prop and propg) were updated. The syntax of the language remained the same, which is great. In C# 2.0, you can declare an abstract class to have a property with the following syntax:

public int X { get; set; }

In C# 3.0, a new feature called "automatic properties" allows you to use this syntax in concrete classes, as well. The compiler automatically creates the private variable for you, but you don't see it, all access is forced through the property, which solves the problems I mentioned in the previous post. You can prepend the get and set with access modifiers as well. For example:

public int X { get; protected set; }

This is a very clean way of doing things, and I feel rather silly for not thinking of it myself. It's a pleasant surprise in C# 3.0, since only the main features ever seemed to be touted (LINQ). It's also backwards compatible, so when I compile RITA to be compatible with .NET 2.0, it works just fine.

Sunday, November 18, 2007

On C# and properties

I flew out to Seattle again this weekend for afternoon tea with Microsoft's CLR and C++ teams. The C++ developer I met was an interesting fellow, having worked on MSVC++ compiler for over 14 years and other C/C++ compilers for even longer. I've never seen someone so passionate about compilers, especially not for C++, but he seemed to take the challenge of C++ and transform it to pure enjoyment.

At one point during our discussion over Thai food for lunch, we started talking about characteristics that constituted "high-quality code", as well as topics in programming languages. Of course, there was no way I could lie my way out and say that C++ is my favorite language—it's probably among the least favorites—but my mention of C# led to some discussion about why I liked C#. I mentioned that C# was basically "Java done right", since Java is pretty clearly a direct predecessor to C#. Of course, no programming language is perfect, and he probably would have thought I was an opinionated jerk if i had said C# was.

Instead I decided to bring up something that I'd been thinking about for the past few days, with our software engineering team to blame. Essentially, I thought that properties should be able to encapsulate private variables properly for maintainers/fellow developers. Obviously they hide private variables and define the interface for designers of other classes, but for the designers of a given class, encapsulation is "broken." The maintainers of the code have two ways to access data (directly through the private variable and through the exposed property), which leads to some unintended problems:

  1. Finding references to a variable is separate from finding references to a property. The case where this is necessary is probably rare, at best. This is demonstrated by the popular use of properties that are simply one line get/sets, which is no different than setting the private variable directly. Removing the private path of access would eliminate this problem, which is an irritation to anyone who might use "Find All References" in Visual Studio, as well as any tool that may perform static analysis on C# code.
  2. If a property does anything besides a one line get/set, private access to the variable means some code that wasn't executed probably should have been. This was colorfully illustrated in our code in which a property had a multi-page set method (which arguably shouldn't have happened, since properties are supposed to be light). Any single incorrect access to the private variable would meant lots of code feeling lonely and would have resulted in a rebellion that would probably bring the program down.

This is a problem that can probably be solved by simply prefixing the private variable with something (like _ or m_), but I can't say I'm a fan of that solution, and it still appears on IntelliSense. I tend to make the capitalization of the first letter the only difference (private members being camelCase and public being PascalCase) and steadfastly believe that prefixes are ugly. Of course, this is probably the only solution without changing C#, so I may have to adopt it in the future, but what fun is not changing C#?

The solution that I suggested that I hadn't completely thought through was for C# properties to be able to embed variables in them. C# properties can only have get/sets inside of them, but consider the following code:

public DateTime Date
{
    DateTime date;
    get { return date; }
    set { date = value; }
}

I think this provides an interesting, additional level of abstraction. If the date variable in the Date property is local to the property, it prevents public access of any kind to it; all access must go through the property. In a sense, you're almost creating a new class to wrap around the data (you can't actually do this in C# since you can't overload the = operator). This means all reference searches would have to be through the property, which fixes both problems I listed above. Although it looks kind of funny, I think it would be a backwards compatible change, since the private variable could theoretically still exist inside or outside the property, depending on the need to access the private variable directly.