DLL vs EXE Link to heading
Dynamic Linked Library, cannot run individually. Executable file have Main function.
Naming Conventions Link to heading
| Object Name | Notation | Length | Plural | Prefix | Suffix | Abbreviation | Char Mask | Underscores |
|---|---|---|---|---|---|---|---|---|
| Class name | PascalCase | 128 | No | No | Yes | No | [A-z][0-9] | No |
| Constructor name | PascalCase | 128 | No | No | Yes | No | [A-z][0-9] | No |
| Method name | PascalCase | 128 | Yes | No | No | No | [A-z][0-9] | No |
| Method arguments | camelCase | 128 | Yes | No | No | Yes | [A-z][0-9] | No |
| Local variables | camelCase | 50 | Yes | No | No | Yes | [A-z][0-9] | No |
| Constants name | PascalCase | 50 | No | No | No | No | [A-z][0-9] | No |
| Field name | camelCase | 50 | Yes | No | No | Yes | [A-z][0-9] | Yes |
| Properties name | PascalCase | 50 | Yes | No | No | Yes | [A-z][0-9] | No |
| Delegate name | PascalCase | 128 | No | No | Yes | Yes | [A-z] | No |
| Enum type name | PascalCase | 128 | Yes | No | No | No | [A-z] | No |
fields vs properties
Link to heading
properties exposes fields. meaning properties have getter and setter whereas fields store actual data.
...
// this is a field
private string _myField;
// this is a property
public string MyProperties
{
get => _myField;
set => _myField = value;
}
...
Numbers
Link to heading
int can be overflowed
class
Link to heading
class modifier:
sealed,abstractClass inheritance: only directly inherit one base class that is not defined as
sealedsealedmodifier prevents other classes from inheriting from it.abstractis intended only to be a base class of other classes.members marked as
abstractmust be implemented by classes that derive from theabstractclass.The
volatilekeyword indicates that a field might be modified by multiple threads that are executing at the same time.C# is both passing by value and reference
if the intent is passing by reference, using keyword
refandoutusingThe reason for theusingstatement is to ensure that the object is disposed as soon as it goes out of scope, and it doesn’t require explicit code to ensure that this happens.
class vs. struct
Link to heading
almost the same, it is recommended that group small data using struct, however, struct can also have methods, properties, fields, constructor, in that case, class is recommended being used.
Square Brackets Link to heading
- array access, like name[0]
- indexer (mainly used for dictionary I guess), like dict[“idx”];
- square brackets in front of classes called Attribute, which is a counterpart of Java annotations, but with differences like assembly level attributes and stuff.
pointers Link to heading
C sharp allows pointers.
use unsafe keyword to allow pointers in code blocks.
unsafe keyword can be used in methods, members.
Exceptions Link to heading
unlike Java, in C# people cannot throw exceptions in signatures.
just throw exceptions inside code block.
Inheritance Link to heading
“:” Link to heading
class Child : Parent
meaning class called Child is derived from class called Parent, and Parent is the base class of Child
base keyword
Link to heading
base class does not have to be an abstract class, it can be a real class.
It is an error to use the base keyword from within a static method.(reason: for static method, there is no current instance. when calls base, it will ask for the base instance of derived instance, conflicted).
override keyword (both inheritance and polymorphism)
Link to heading
The overridden base method must be virtual, abstract, or override
Polymorphism(C# polymorphism is more flexiable than java) Link to heading
initiate an instance of Interface
接口不能实例化!但是如果非要 实现接口的类 实例 = new 实现接口的类() 那要接口有什么用?
接口 实例 = new 实现接口的类A()
接口 实例 = new 实现接口的类B()
接口 实例 = new 实现接口的类C()
We can create a new Class D that implements this Interface to encapsulate method ABC. This is the Factory Mode
Encapsulation Link to heading
Access Modifier
public: access is not restrictedprotected: Access is limited to the containing class or types derived from the containing class. (in other words, this class and/or subclass)internal: (seems like protected internal is more valuable)private: Access is limited to the containing type
“::” Link to heading
called The namespace alias qualifier
“?” after a type Link to heading
meaning the value of type is nullable.
Nullable types are declared in one of two ways:
System.Nullable<T> variable
-or-
T? variable
“??” or null coalescing operator Link to heading
string Answer = Answer1 ?? Answer2;
Translation in English is that “if whatever in left is NOT null, use that, otherwise, use what is to the right”.
“@” before a string Link to heading
It means to interpret the string literally (that is, you cannot escape any characters within the string if you use the @ prefix)
Generics in C# Link to heading
// Declare the generic class.
public class GenericList<T>
{
public void Add(T input) { }
}
class TestGenericList
{
private class ExampleClass { }
static void Main()
{
// Declare a list of type int.
GenericList<int> list1 = new GenericList<int>();
list1.Add(1);
// Declare a list of type string.
GenericList<string> list2 = new GenericList<string>();
list2.Add("");
// Declare a list of type ExampleClass.
GenericList<ExampleClass> list3 = new GenericList<ExampleClass>();
list3.Add(new ExampleClass());
}
}
The most common use of generics is to create collection classes
You can create your own generic interfaces, classes, methods, events and delegates
more advanced about generic classes, firstly know some concepts: concrete type, closed constructed type, open constructed type
Generic classes can inherit from concrete, closed constructed, or open constructed base classes:
class BaseNode { }
class BaseNodeGeneric<T> { }
// concrete type
class NodeConcrete<T> : BaseNode { }
//closed constructed type
class NodeClosed<T> : BaseNodeGeneric<int> { }
//open constructed type
class NodeOpen<T> : BaseNodeGeneric<T> { }
Non-generic classes can only inherit concrete or closed structured base classes.
//No error
class Node1 : BaseNodeGeneric<int> { }
//Generates an error
//class Node2 : BaseNodeGeneric<T> {}
//Generates an error
//class Node3 : T {}
Generic classes can also do some I-call-it smart mapping
class BaseNodeMultiple<T, U> { }
//No error
class Node4<T> : BaseNodeMultiple<T, int> { }
//No error
class Node5<T, U> : BaseNodeMultiple<T, U> { }
//Generates an error
//class Node6<T> : BaseNodeMultiple<T, U> {}
Generic classes that inherit from open constructed types must specify constraints that are a superset of, or imply, the constraints on the base type:
// constraints on T
class NodeItem<T> where T : System.IComparable<T>, new() { }
class SpecialNodeItem<T> : NodeItem<T> where T : System.IComparable<T>, new() { }
...
class SuperKeyType<K, V, U>
where U : System.IComparable<U>
where V : new()
{ }
Interfaces Link to heading
By convention, interface names begin with a capital I.
interface IEquatable<T>
{
bool Equals(T obj);
}
To implement an interface member, the corresponding member of the implementing class must be public, non-static, and have the same name and signature as the interface member.
Any class implements interface IEquatable<T> must provide an implementation of Equal method.
Example:
public class Car : IEquatable<Car>
{
public string Make {get; set;}
public string Model { get; set; }
public string Year { get; set; }
// Implementation of IEquatable<T> interface
public bool Equals(Car car)
{
return this.Make == car.Make &&
this.Model == car.Model &&
this.Year == car.Year;
}
}
events and delegates Link to heading
we’d like to be able to pass it to somebody else so that they can call it. This is especially useful in an event-driven system such as a graphical user interface, when I want some code to be executed when the user clicks on a button, or when I want to log some information but can’t specify how it is logged.
The signature of a single cast delegate is shown below:
delegate result-type identifier ([parameters]);
Examples:
public delegate void SimpleDelegate ()
This declaration defines a delegate named SimpleDelegate, which will encapsulate any method that takes no parameters and returns no value.
public delegate int ButtonClickHandler (object obj1, object obj2)
This declaration defines a delegate named ButtonClickHandler, which will encapsulate any method that takes two objects as parameters and returns an int.
Let’s see a more advanced example
using System;
using System.IO;
namespace Akadia.SimpleDelegate
{
// Delegate Specification
public class MyClass
{
// Declare a delegate that takes a single string parameter
// and has no return type.
public delegate void LogHandler(string message);
// The use of the delegate is just like calling a function directly,
// though we need to add a check to see if the delegate is null
// (that is, not pointing to a function) before calling the function.
public void Process(LogHandler logHandler)
{
if (logHandler != null)
{
logHandler("Process() begin");
}
if (logHandler != null)
{
logHandler ("Process() end");
}
}
}
// The FileLogger class merely encapsulates the file I/O
public class FileLogger
{
FileStream fileStream;
StreamWriter streamWriter;
// Constructor
public FileLogger(string filename)
{
fileStream = new FileStream(filename, FileMode.Create);
streamWriter = new StreamWriter(fileStream);
}
// Member Function which is used in the Delegate
public void Logger(string s)
{
streamWriter.WriteLine(s);
}
public void Close()
{
streamWriter.Close();
fileStream.Close();
}
}
// Test Application which calls both Delegates
public class TestApplication
{
// Static Function which is used in the Delegate
static void Logger(string s)
{
Console.WriteLine(s);
}
static void Main(string[] args)
{
FileLogger fl = new FileLogger("process.log");
MyClass myClass = new MyClass();
// Crate an instance of the delegates, pointing to the static
// Logger() function defined in the TestApplication class and
// then to member function on the fl instance of a FileLogger.
MyClass.LogHandler myLogger = null;
myLogger += new MyClass.LogHandler(Logger);
myLogger += new MyClass.LogHandler(fl.Logger);
myClass.Process(myLogger);
fl.Close();
}
}
}
Compile an test:
# csc SimpleDelegate4.cs
# SimpleDelegate4.exe
Process() begin
Process() end
# cat process.log
Process() begin
Process() end
This is called multicasting. Being able to point to member functions is nice, but there are more tricks you can do with delegates. In C#, delegates are multicast, which means that they can point to more than one function at a time (that is, they’re based off the System.MulticastDelegate type).
Data Structures in C# Link to heading
ArrayList: a dynamic array. Usage:ArrayList myArrayList = new ArrayList();ArrayListdoesn’t implicit any type, so accept different objects.List<T>: single type elementsArrayListLinkedList<T>: DOUBLY linked list. Cool! and also I can grabLinkedListNode<T>using eitherFirstorLastStack<T>:Push(),Pop(),Peek()Queue<T>:Contains(),Enqueue(),Dequeue(),Peek()HashSet<T>:bool Add(), bool Contains(), IntersectWith(), Remove()Dictionary<TKey, TValue>: C#’s Dictionary uses [] indexing for setting/getting itemsmyDictionary[key] = value; bool TryGetValue();
LINQ Link to heading
Lamda (Method) Syntax
var longWords = words.Where( w ⇒ w.length > 10); Dim longWords = words.Where(Function(w) w.length > 10)Query (Comprehension) Syntax
var longwords = from w in words where w.length > 10; Dim longwords = from w in words where w.length > 10
LINQ to SQL (DLINQ)
Unit Tests Link to heading
Here take Nunit as example.
I found cannot using namespace right away, that is because I don’t reference.
Add a Reference to Your Project
In order to test the code in your main project, you need to add a reference to it in your test project.
- Right click on your test project
- Click on Add | Reference…
- Select Projects | Solution
- Add a checkmark on your main project.
- Click OK.
open the Test Explorer Window.
To do this, in the main menu, click Test | Windows | Test Explorer.
Click Run All to run your tests