This is a very brief introduction on how to use C# for developers familiar with Java.  The other resources I have found on the internet are reference-style and very long or feel too academic.  This is for people who want a very quick start into using C# and are planning to learn the full language as they go.  I hope it helps!If you actually are looking for a more complete reference, I recommend Dare Obasanjo’s C# To Java Overview.I have divided this guide into 3 sections. If you want to know the basics, read “Should Know”.  If you want to learn about some features that you may find useful, but probably aren’t necessary for you to start programming in C#, check out “Could Know”.  “Quick reference” is pretty self-explanatory, just Java keywords and their C# equivalents!

Should Know

The first thing to know is that luckily for you, C# and Java are very similar!  Quite a bit of Java code could be copy pasted into a C# IDE and compiled without errors, apart from some minor syntax issues.  However, Java and C# have some differences that you must know before you start coding in C#.  Let’s look at a code comparison.

Syntax

Java:

public class Tester 
{
    public static void main(string[] args)
    {
        boolean isRunning = true;
        String str = "I'm a string!";
        MyClass abc = new MyClass();

        for(int i=0; i < 10000; i++)
          abc.Process(i + str);
   }
}
C#:
public class Tester 
{
    public static void Main(string[] args)
    {
        bool isRunning = true;
        string str = "I'm a string!";
        MyClass abc = new MyClass();

        for(int i=0; i < 10000; i++)
          abc.Process(i + str);
   }
}

Pretty similar, right?  Here are a couple basic syntax differences you should know off the bat.  Check out the quick reference section for more syntax differences.

A Java "boolean" is a C# "bool".
A Java variable defined as final is like a C# const.
The "Main" method in C# is capitalized but in Java, "main" is not.
To import a class in Java you use "import", but in C# the term is "using".
For Java, inheriting a class uses "extends" and inheriting and interface uses "implements", but in C# both are indicated by a ":".

Your IDE will often auto-correct small syntax differences, but looking at other people's code will often reveal varying syntax.  Learn it as you go.

Inheritance

As I said before, C# and Java use slightly different syntax for inheritance.
Java:

public class B extends A implements Comparable 
{ ... }
C#:
public class B : A, IComparable 
{ ... }

Calling Base Constructors

To call a superclass’s constructor in Java, you use super().
In C#, use base() in a similar way.
Java:

public Game(int level)
{
    super(level);
}

C#:

public Game(int level)
: base(level)
{

}

Calling Overriden Methods

Java and C# both require knowledge that a base class’s method
should override a superclass’s method.  To call the original
method within that, use base.
Java:

@Override
public void Update()
{
super.Update();
}

C#:

public override void Update()
{
base.Update();
}

Foreach loops

The syntax for foreach loops is a little different between the languages.
Java:

for(int n : elements)
{ ... }

C#:

foreach (int n in elements)
{ ... }

Default Accessibility

In Java, when you don’t specify a class’s scope, it is protected by default.  In C# it will be internal, which means it can only be accessed from the same package.
Java:

class A //this class is protected
{
protected int _i;
}

C#:

class A //this class is internal
{
protected int _i;
}

 


Structs

This concept is different from anything in the Java language.  Structs look like classes and are initialized with the new operator just like classes, but they are treated like value types (ex. int).  Treat them like lightweight classes that are always passed by value (copied when passed as a parameter).  They also cannot inherit other classes or structs.
C#:

public struct Point
{
public int x;
public int y;

public Point(int pX, int pY)
{
x = pX;
y = pY;
}
}

Properties

In C#, classes and structs can have properties which act like getter and setter methods in Java.  They are called externally like public instance variables but are different because they hide the implementation details of the class.  They are context sensitive so a single property can act as both a get and a set!
C#:

public string Name
{
get
{
if (_myName == null)
return “Unnamed”;
else
return _myName;
}
set
{
_myName = value;  //value is whatever you pass into the property at a set
}
}

If this property was inside MyClass, you could call it like this.  Note how a property acts as a getter or a setter depending on the context.
C#:

MyClass c = new MyClass();
c.Name = “Alex”;  //calls the setter
string str = c.Name; //calls the getter

Could Know

These techniques are very likely to increase your programming efficiency if you have been trying out C#, understand the very basics, and want to know more about what C# can do for you.

Passing By Reference

Unlike Java, C# allows us to pass variables by reference instead of only by value (although by default it behaves the same as Java).out – use to get an uninitialized variable and give it a value.

C#:
publlic void Assign(out string s)
{
s= new string(“Hi”);
}

ref – use it to change an already initialized variable
Using this we can do a very simple thing that Java has difficulty with, modifying two objects within a single function.

C#:
public void Swap(ref string s, ref string r)
{
string temp = s;
s = r;
r = temp;
}

Nullable Types

Primitives usually can’t be set to null, for example a boolean is always either true or false.  But with nullable types, you can make a nullable boolean which can have a value of true,false, or null.  Just add a “?” to the type.  The same goes for ints.
C#:
int? x = 5;

if(x.HasValue)
{
Console.WriteLine(“The value of x is ” + x.Value);
}
x = null;

//prints 0
Console.WriteLine(x.GetValueOrDefault());

Operator Overloading

Like C++, we can overload operators for our own objects.
C#:
public static MyInteger operator -(MyInteger n)
{
return new MyInteger (-n.value);
}

Defining Identifiers In Pre-Processing

C# gives us the ability to create variables that are evaluated before compiling the file.  This is very useful if we want to for example define sections that should only occur in debugging.
We put these directives at the top of the file.
C#:
#define DEBUG

elements(i) = CalculateElement(i);#if DEBUG
log.Info(“Our current element is currently: ” + elements(i).ToString());
#endif
…Since DEBUG is a pre-processing directive, our if statement will be evaluated before we compile our project.  That means if we are building for a non-debug environment, anything within the DEBUG directive would be ignored at compilation.

In XNA, there are other pre-defined directives like #if WINDOWS and #if XBOX so we can write a single source file for multiple target platforms.  You can also define how some functions handle math.

Iterators

Sometimes, we want a property or method to behave like an Enumerator, but we don’t want to write a lot of code when the actual logic is quite simple.  Using the yield keyword, we can make simple logic for an IEnumerable/IEnumerator.
C#:
public static string[] fruit = {“banana”, “apple”, “orange”, “pear”, “grape”};
public static string[] vegetables = {“lettuce”, “cucumber”, “peas”, “carrots”};
public static IEnumerable FruitAndVeg{
get{
foreach(string f in fruit){ yield return f; }
foreach(string v in vegetables){ yield return v; }
yield break; //optional
}
}

public static void Main()
{
foreach (string produce in Test.FruitAndVeg)
{
Console.WriteLine(produce);
}
}

Partial Classes

Classes can be implemented in multiple files with the partial keyword.

C#:

partial class Test{

Defining Aliases

Similar to typedef in C++, we can reduce our keystrokes by creating aliases with the using keyword.
C#:
using C = System.Console;…
C.WriteLine(“blah”);

Just be sure to not abuse it; if you alias too many things, your code will become very difficult for another programmer to read!

Quick Reference

C# keyword Java keyword C# keyword Java keyword C# keyword Java keyword C#keyword Javakeyword
abstract abstract extern native operator N/A throw throw
as N/A false false out N/A true true
base super finally finally override N/A try try
bool boolean fixed N/A params typeof N/A
break break float float partial N/A uint N/A
byte N/A for for private private ulong N/A
case case foreach for protected N/A unchecked N/A
catch catch get N/A public public unsafe N/A
char char goto goto readonly N/A ushort N/A
checked N/A if if ref N/A using import
class class implicit N/A return return value N/A
const const in N/A sbyte byte virtual N/A
continue continue int int sealed final void void
decimal N/A interface interface set N/A volatile volatile
default default internal protected short short where extends
delegate N/A is instanceof sizeof N/A while while
do do lock synchronized stackalloc N/A yield N/A
double double long long static static

:

extends
else else namespace package string N/A

:

implements
enum N/A new new struct N/A N/A strictfp
event N/A null null switch switch N/A throws
explicit N/A object N/A this this N/A transient

 

 

Leave a Reply