Translating Objective-C to C# – Part 2 of n

I hope by now you’ve already read Part 1, and if not, go do so now! As I left off last time I mentioned that I’d cover interfaces vs. implementations, type checking, inheritance, alloc-init, polymorphism, self/this and super/base keywords, properties, and initializers from Chapters 4-5 of the excellent book Programming iOS 5, Second Edition.
These 2 chapters get a little more in-depth into understanding Objective-C enough that you can then go and understand the basic Cocoa usage examples. This might be the last post purely about the Objective-C and C# languages, but I hope to get into more of a framework discussion of translating Cocoa to XAML for Windows Phone or Windows 8 Metro app development.
Again, I’ll be using a subset of the examples from the book as the source, but to fully understand the context, I recommend picking up a physical or eBook copy as it really is an excellent book!

Interface vs Implementation

At first, I assumed that Objective-C interfaces were much like C# interfaces in that they define the methods that a concrete type implements (and Objective-C actually uses the @implementation keyword for the concrete type), but after getting to the Cocoa examples, I realized this is not the case.
An Objective-C interface is pretty much an equivalent of a C++ header file (and, in fact, if you have the interface in a separate file, it uses a .h file extension, just like a C++ header file). It does not define an interface that other types can use as a contract – that’s what protocols are for, which I’ll cover later.
In Objective-C, you must have an @interface and an @implementation for classes you create. They can be in the same file or in separate files (the @interface in a .h file, and the @implementation in a .m file). In C#, you do not need a “header” for defining a class – this information is extracted as metadata at compile time.
Here’s the example of a trivial, single-file interface and implementation:
@interface MyClass : NSObject
- (NSString*) sayGoodnightGracie;
@end
@implementation MyClass
- (NSString*) sayGoodnightGracie {
return @"Good night, Gracie!";
}
@end

Notice that the @interface is where the inheritance is defined – MyClass here inherits from NSObject. There is a single instance (non-static) method called sayGoodnightGracie, and its signature is defined in the @interface and implemented in the @implementation. Notice that the interface and implementation share the same name – that should be your first clue that interfaces in Objective-C are not the same as interfaces in C#, as a class cannot share the same name (in the same namespace) as an interface it implements (or any other type, for that matter).
In C# meanwhile, the class is a bit simpler to define:
public class MyClass
{
    public string SayGoodnightGracie()
    {
        return "Good night, Gracie!";
    }
}

Now I’ll temporarily deviate from the book’s order to cover protocols, because they are what is equivalent to C#’s (or rather the CLI’s) interfaces. Like I mentioned, an Objective-C protocol is equivalent to a C# interface. Often you may read/hear Objective-C developers refer to protocols as delegates, as they are often used in a delegation pattern by Cocoa types, but a protocol itself does not innately imply delegation. If we wanted to create a protocol for the MyClass above, here’s what it might look like in Objective-C:
@protocol ISayGoodnightGracie <NSObject>
@required
- (NSString*) sayGoodnightGracie;
@end

Notice that the @required keyword means that any signatures following it must be implemented in the concrete types – there is no equivalent to this in C#. If a C# interface defines a signature, it must be implemented by the inheriting type.
Now, in order for MyClass to implement ISayGoodnightGracie, we use a special syntax using angle brackets. Also, we remove the signature from the @interface since it is now defined in the @protocol:
@interface MyClass : NSObject <ISayGoodnightGracie>
@end

@implementation MyClass
- (NSString*) sayGoodnightGracie {
return @"Good night, Gracie!";
}
@end

To translate this to C#, we define a new public interface called ISayGoodnightGracie, and make MyClass inherit from it using a colon delimiter:
public interface ISayGoodnightGracie
{
    string SayGoodnightGracie();
}

public class MyClass : ISayGoodnightGracie
{
    public string SayGoodnightGracie()
    {
        return "Good night, Gracie!";
    }
}

Type Checking

Now, back to where the book left off. Next up is type checking – or, checking whether an instance inherits from a given type in its inheritance heirarchy.
You might think this is similar to .NET’s Reflection, and it is, to a small extent. Each class in Objective-C has a corresponding Class instance, which is roughly equivalent to the System.Type type in .NET. You can get a class’ Class instance in Objective-C like this:
Class c = [MyClass class];
Which is mostly equivalent to the typeof operator in C#:
Type t = typeof(MyClass);
One major difference, however, is that you can send messages to static (class) methods to that “c” variable above – something you cannot do in C# to the “t” variable above.
You can also get the Class of a given object instance using the same “class” method:
MyClass* m = // something or other...
Class c = [m class];

And in C#, this is equivalent to the Object.GetType instance method:
MyClass m = new MyClass();
Type t = m.GetType();

Again, the same limitation of static method calls in C# applies.
Now that you can see how you can get type information, hopefully that will help in understanding determining inheritance. Objective-C has a way of checking to see if an object instance inherits from a type, using the isKindOfClass method, defined like this:
- (BOOL)isKindOfClass:(Class)aClass
In the book, it is used like this, in an if statement:
if ([someObject isKindOfClass: [MyClass class]]) // ...
C# has a few methods to determine inheritance. The most direct translation of the method above would be to use the “is” keyword:
if (someObject is MyClass) //...
This will work for exact matches as well as looking up the inheritance heirarchy, just like isKindOfClass does. You can use isMemberOfClass for exact matches in Objective-C, while you can use someObject.GetType() == typeof(MyClass) in C# to do an exact comparison.

[[MyClass alloc] init] and Initializers

Repeatedly in Objective-C you will see code equivalent to the following, known as the “alloc-init pattern”:
MyClass* m = [[MyClass alloc] init];
The inner message allocates space in memory to hold an instance of MyClass based on its known size, while the init message call performs any default initialization of instance variables or other initialization tasks. It then returns a pointer to the newly created object. According to the book, you will almost never want to separate these out into separate lines (i.e. storing just the result of alloc to a variable, then calling init), and as I’m just learning Objective-C, I can’t foresee a situation where you would need to. (I would appreciate if someone could outline for me an example where you might want to break with this pattern and do so – as well as what the dangers would be.)
In C#, the allocation of a new instance of a type is accomplished with the “new” keyword, and which constructor (equivalent to initializers in Objective-C) to call is determined by the parameters following the type name. The “init” message above is a default, parameterless initializer, which is much like a default, parameterless constructor in C#. Like I mentioned in the previous post, the pointers are implicitly managed for you, so you do not need the asterisk. The Objective-C example above would be equivalent to the following in C#:
MyClass m = new MyClass();
You will find that there are parameter-based initializers as well, such as NSArray’s initWithObjects initializer:
NSArray* pep = [[NSArray alloc] initWithObjects:@"Manny", @"Moe", @"Jack", nil];
This initializer would be equivalent to the following constructor, if you recreated the NSArray type in C# and didn’t reuse the BCL array type:
public NSArray(params object[] objects) { … }
Which would be called like this:
NSArray pep = new NSArray("Manny", "Moe", "Jack");
One major difference between Objective-C initializers and C# constructors is that C# (or rather .NET’s CLI) doesn’t use different identifiers for different constructors, they are merely method overloads if you have more than one – whereas the above Objective-C “initWithObjects” is clearly a different identifier than just “init”.
Also note in this example that variable-length arguments must end with nil as a terminator in Objective-C, but that is not required in C#.
There also is the concept of default initializers in Objective-C, where other initializers must ultimately call the default one – but there is no such requirement amongst instance constructor overloads in C#, although it is possible with constructor chaining:
public MyArray(params object[] objects) { /* ... */ }
public MyArray(List<object> objects) : this(objects.ToArray()) { }
In the above example, if you pass a List<object> into the MyArray constructor, it will pass the list as an array to the variable-length constructor overload.

Polymorphism

Polymorphism in Objective-C works very much like a C# developer would expect. You can implicitly cast an object to one of it’s inherited types upon assignment, like in this example from the book, where UIButton inherits from UIControl, which in turn inherits from UIView:
UIButton* b = [UIButton buttonWithType:UIButtonTypeRoundedRect];
UIView* v = b;

If these types existed in .NET, the previous code might look like this:
UIButton b = UIButton.ButtonWithType(UIButtonType.UIButtonTypeRoundedRect);
UIView v = b;

Both examples demonstrate the implicit conversion between a child class and a class higher up in its inheritance heirarchy. Much like C#, in Objective-C you can’t call a method on a variable of the higher class (UIView) that is defined in the lower class (UIButton) without an explicit cast (except without ARC enabled, in which case you’ll get a compiler warning). So the following would be illegal Objective-C with ARC enabled:
UIButton* b = [UIButton buttonWithType:UIButtonTypeRoundedRect];
UIView* v = b;
[v setTitle:@"Howdy!" forState:UIControlStateNormal];

But if you cast V to UIButton, it does work:
UIButton* b = [UIButton buttonWithType:UIButtonTypeRoundedRect];
UIView* v = b;
[(UIButton*)v setTitle:@"Howdy!" forState:UIControlStateNormal];

Likewise, here’s an illegal C# example of the above code:
UIButton b = UIButton.ButtonWithType(UIButtonType.UIButtonTypeRoundedRect);
UIView v = b;

v.SetTitle("Howdy!", UIControlState.UIControlStateNormal);
But the following is legal, since we’ve cast v to the type that defines SetTitle:
UIButton b = UIButton.ButtonWithType(UIButtonType.UIButtonTypeRoundedRect);
UIView v = b;

((UIButton)v).SetTitle("Howdy!", UIControlState.UIControlStateNormal);

Self vs This and Super vs Base

Objective-C’s “self” keyword behaves very similarly to C#’s “this” keyword. In a simple, single-level class, the self/this keywords refer to the current instance of the class that the method is being executed on. In a parent/child class example, if you refer to the self/this keyword in a parent-level method, it can refer to an instance of the child class. This applies to virtual method calls in C#, much as it does overridden methods in Objective-C.
In the book, he uses an example where a parent class Dog has a child class Basenji, where the parent class Dog’s “bark” method is overridden to return an empty string in the child Basenji class, because Basenji’s can’t bark. Yet, when the parent class’ “speak” method calls [self bark], the “self” is referring to the most inherited version of the method for the current instance, not the “bark” method on the parent class:
@implementation Dog
- (NSString*) bark {
return @"Woof!";
}
- (NSString*) speak {
return [self bark];
}
@end
@implementation Basenji : Dog
- (NSString*) bark {
return @""; // empty string, Basenjis can't bark
}
@end
// [so, in some other class...]
Basenji* b = [[Basenji alloc] init];
NSString* s = [b speak];

This behaves the same in C# with virtual method calls:
public class Dog
{
    public virtual string Bark()
    {
        return "Woof!";
    }

    public string Speak()
    {
        return this.Bark();
    }
}

public class Basenji : Dog
{
    public override string Bark()
    {
        return "";
    }
}

// somewhere later on...
Basenji b = new Basenji();
string s = b.Speak();

Just like in Objective-C, this C# code would store an empty string to the s variable, because calling “this.Bark()” will call Basenji’s overridden method.
Much like self/this, the Objective-C “super” keyword is analogous to C#’s “base” keyword, and calls to parent class methods (like virtual methods in C# calling the base version) using the super/base keyword work much the same way.

Properties

Objective-C and C# share a powerful feature that Java still lacks – properties. Properties allow you to encapsulate a field with getter and setter methods while still allowing it to feel like you’re working with a field rather than methods. To define a property in Objective-C, you use the @property keyword in your interface:
@property (nonatomic, retain) NSString* MyProperty;
If you want to define the getter and setter methods yourself, you can use the @dynamic keyword in your implementation. (I’m a little fuzzy on this, so please someone correct me if I’m on the wrong track.)
@implementation MyClass {
    @private NSString* _myProperty;
}

@dynamic MyProperty;
- (NSString*) MyProperty {
    return _myProperty;
}
- (void) setMyProperty:(NSString*)value {
    self->_myProperty = value;
}

@end
The @dynamic keyword tells the compiler that you will supply get and set methods for the property of MyProperty. The equivalent in C# (including the @property declaration) would be:
public class MyClass
{
    private string _myProperty;
    public string MyProperty
    {
        get { return _myProperty; }
        set { _myProperty = value; }
    }
}

As an alternative to the @dynamic keyword with properties, you can use the @synthesize keyword to tell the compiler to automatically create getter/setter methods for you, as well as a backing field.
@implementation MyClass
@synthesize MyProperty;
@end

In C#, there is the automatic property syntax to do the same thing:
public class MyClass
{
    public string MyProperty { get; set; }
}

One feature that Objective-C has that C# lacks is the ability to automatically create get/set methods around a named private field that you have access to. C# will automatically create a backing field for each property, but it is given a special name by the compiler and you do not have access to it without some heavy (and largely unnecessary) reflection. To use this feature of Objective-C, add the private field name with an equals sign after the property name you’re synthesizing:
@synthesize MyProperty = _myProperty;
It would be great if C# would add equivalent functionality in the future, but that doesn’t appear to be on the roadmap.
Also of note is that C# lacks property attributes – in the interface example, the attributes are “nonatomic, retain”. These attributes signal to the compiler how to treat the accessor methods – nonatomic signals that the get/set methods should not be treated in a thread-safe manner and any thread safety should be left up to the implementation method if needed, and retain says that the passed-in variable should be retained before setting the instance variable. Since these (and other) property attributes have no C# equivalent, I’ll leave them for another day.

Summary

Hopefully this has shed some more light on how Objective-C and C# are really not all that different if you can apply a little bit of translation in your head while reading/writing code. If you live near Jacksonville, I hope you’ll come out to my presentation on iPhone Development with a Windows Azure-hosted API at JaxDUG on June 6th.
Please give me feedback on these posts in the comments. Thanks!
Previous
Next Post »