Possible Duplicate:
Most common or vicious mistakes in C# development for experienced C++ programmers
I'm a long time C++ programmer about to start working on C# projects.
What are some conceptual changes to be aware of, and most importantly, what should I avoid doing in C# that I would normally do in C++? What bad habits do C++ programmers bring to C# that they should lose?
I have a list of C# books I intend to read. I'd like to augment that with experiences from other programmers that have made this same transition becaus开发者_StackOverflow中文版e I'll probably tend to make the same errors they did; I'd like to prevent that before it happens.
Just one example:
In C++ there is no difference between a struct and a class. Over the years this has led groups and individuals to define their own rules for using one over the other.
In C# there is a concrete difference. A struct is a value type and a class is a reference type.
When C++ programmers bring thier old, arbitrary class/struct definitions to C#, unexpected things tend to happen.
Here is a fairly good read for C++ programmers moving to C#: http://msdn.microsoft.com/en-us/magazine/cc301520.aspx
One thing to be aware of is that C# doesn't have destructors in the same sense as C++ does. A method with the signature of a C++ destructor is called a finalizer in C# and it's not necessary (and in some cases not recommended) to implement those.
Check out the IDisposable interfaceand these articles on garbage collection: Everybody thinks about garbage collection the wrong way and Garbage Collection: Automatic Memory Management in the Microsoft .NET Framework.
- there is no implicit RAII, you have to explicitly code it
- there is no const protection
- properties are pairs of methods, not a value
- when iterating you start before collection and end at the end of it (in terms of C++)
- foreach is like using const_iterator
- List as the name says, is not a list, is a an array
- generics are resolved at their compile time, not at time of using them
The big ones:
- C# doesn't have multiple inheritance, it uses interfaces instead.
- You can't control the lifetime of an object or use that to your advantage.
- The C# equality operator doesn't always do what you think it should. Sometimes it compares the content of a variable and sometimes the address of the variable.
Worst I have seen is
1) overly using Critical Context (locking using Monitor or lock() statement) in a web project! Result quite often is reducing IIS to a more-or-less single-threaded system.
2) Too much string processing. Used to do everything themselves so not relying on framework. Strings are immutable in C# while they are not in C++.
3) Using unsafe code because they can and not because they should.
4) Not trusting GC
Not much, moving from C++ to C# is a sort of degradation, so you can't do "Bad things". The only thing I can think of is relying on automatic memory management:
class A {
ofstream file;
public:
// bla bla
};
In C# you need to implement all the IDisposable garbage to not leak the file... You can easily forget it.
Bad C# programmer behaviors in C++ would be a more interesting topic.
There's stuff you can do in C++ that you can't do in C#, and vice versa. They aren't likely to cause you problems.
Biggest change - getting rid of the "instantiation is initialization" mindset. Garbage collection means you don't need to worry about allocating or freeing memory (except when you do), but it also means you can't rely on something falling out of scope triggering the destructor to clean up after you.
Learn the "using" construct, in C#, and make sure you use it.
Second change - in C++ "class" and "struct" are effectively synonyms. In C#, they are very different things.
It's not a "bad" habit, but something you definitely need to keep in mind when switching from C++ to C#: relying on destructors to do your cleanup. Instead, you need to remember to implement IDisposable
and control your object's lifetime by a using
statement.
Things to change when moving from C++ to C#:
- Use properties when possible to represent class member data
- Use interfaces in situations that might call for multiple inheritance in C++
- Use events for notification instead of handing callback functions (delegates) to classes
- Remember to use the using() {} construct to ensure that resources like files and DB connections are disposed when they go out of scope.
That's just off the top of my head
The biggest shift for me was to stop worrying about freeing memory, thread safety (I mean you still have to lock things, but C# is designed for threading from day 1 so there are no nasty gotchas) and header files.
If you feel tempted to use /unsafe you are almost certainly wrong.
Learn the class library.
精彩评论