# C# Overview
###### tags: `Class` `Enum` `陣列`, `C#`
>取自 `Jia0` 的筆記
>[time=Fri, Jun 7, 2018]
## Object
是call by reference喔!
舉例:
```cpp=
class ObjectTest
{
public int i = 10;
}
class Program
{
static void Main(string[] args)
{
ObjectTest classRef = new ObjectTest();
ObjectTest anotherClassRef = classRef;
Console.WriteLine("Before Changed :{0}", classRef.i); // 10
anotherClassRef.i = 20;
Console.WriteLine("After Changed :{0}", classRef.i); // 20
}
}
```
## Enum
[官方參考](https://docs.microsoft.com/zh-tw/dotnet/csharp/language-reference/keywords/enum)
> 有互相轉換效果的自訂型態~
> 也許能用它來做 `dictionary`(?
> [name=徐遠志][color=#d5f970]
```csharp=
public enum ShippingMethod
{
RegularAirMail = 1,
RegisterAirMail = 2,
Express = 3
}
var method = ShippingMethod.Express;
(int) method; // 3
method; // Express
var methodId = 3;
(ShippingMethod) methodId; // Express
```
## 陣列們
### 1. [ ]
特定類型、固定長度
```csharp=
//宣告一個陣列並給初始值
string[] arr = new string[] {"a","b"} ;
//宣告一個長度是5的陣列
string[] arr1 = new string[5];
arr1[0] = "lorem";
Console.WriteLine(arr1[0]); //lorem
//數長度
arr.Length; //2
```
### 2. List
特定類型、任意長度
用法整理>>[連結](https://msdn.microsoft.com/zh-tw/library/6sh2ey19(v=vs.110).aspx)
```csharp=
List<int> numsList = new List<int>() { 5, 61, 2, 7, 4, 13, 20 };
numsList.Add(1);
numsList.AddRange(new int[3] { 5, 6, 15});
Console.WriteLine(numsList.LastIndexOf(5)); // 8
Console.WriteLine(numsList.IndexOf(5)); // 0
numsList.Remove(61); // 刪除61,若有重複元素的可以用forLoop
numsList.Clear(); // numsList.Count == 0
//數長度
numList.Count; //11
```
### 3. Array
任意類型、固定長度
> 也是可以做`dictionary`的`key-value pair`形式呢![color=#d5f970]
```csharp=
Array num = Array.CreateInstance(typeof(String), 3);
num.SetValue("one", 1);
num.SetValue("two", 2);
Console.WriteLine(num.GetValue(2)); //two
//數長度
num.Length; //3
```
很多好用的性質~
```csharp=
var nums = new int[] { 1, 2, 3, 4, 5, 6 };
Array.Clear(nums, 3,3); // 1 2 3 0 0 0
var copyNums = new int[2];
Array.Copy(nums, copyNums, 2);
foreach(var i in copyNums) Console.WriteLine(i);
// 1 2
Array.Sort(nums); // 0 0 0 1 2 3
Array.Reverse(nums); // 3 2 1 0 0 0
```
### 4. ArrayList
任意類型、任意長度
[官方參考](https://msdn.microsoft.com/zh-tw/library/system.collections.arraylist(v=vs.110).aspx)
```csharp=
ArrayList list = new ArrayList();
//加東西的方式和 list 一樣
list.Add(0);
list.Add("wendee");
Console.WriteLine(list[0]); //0
Console.WriteLine(list[1]); //wendee
//數長度
list.Count; //2
```
```csharp=
// [[1],[[2],[3]]
// 第1種
ArrayList list = new ArrayList();
list.Add(new int[]{ 1 });
list.Add(new int[,]{ { 2 },{ 3 } });
// 錯誤示範,目前不知道怎麼求
Console.WriteLine(((int[,])((ArrayList)list[1]))[0]);
// 或者是第2種
ArrayList list = new ArrayList();
list.Add(new int[] { 1 });
list.Add(new ArrayList());
((ArrayList)list[1]).Add(2);
((ArrayList)list[1]).Add(3);
Console.WriteLine(((ArrayList)list[1])[0]); //2
```
## 複製Class
* [官方參考](https://msdn.microsoft.com/zh-tw/library/system.object.memberwiseclone(v=vs.110).aspx)
* [StackOverflow](https://stackoverflow.com/questions/6569486/creating-a-copy-of-an-object-in-c-sharp?utm_medium=organic&utm_source=google_rich_qa&utm_campaign=google_rich_qa)
```csharp=
namespace ConsoleApp1
{
class CopyObj
{
private string _name;
public CopyObj(string name)
{
this._name = name;
}
public string name
{
get { return _name; }
set { _name = value; }
}
public String text = "string text in the Object";
public Int16 Id = 34;
public object Copy()
{
return this.MemberwiseClone();
}
}
}
```
```cpp=28
using System;
namespace ConsoleApp1
{
public class IdInfo
{
public int IdNumber;
public IdInfo(int IdNumber)
{
this.IdNumber = IdNumber;
}
}
public class Person
{
public int Age;
public string Name;
public IdInfo IdInfo;
public Person ShallowCopy()
{
return (Person) this.MemberwiseClone();
}
public Person DeepCopy()
{
Person other = (Person) this.MemberwiseClone();
other.IdInfo = new IdInfo(IdInfo.IdNumber);
return other;
}
}
class Program
{
static void Main(string[] args)
{
// 起初,只有一個人
Person p1 = new Person();
p1.Age = 42;
p1.Name = "Sam";
p1.IdInfo = new IdInfo(6565);
// p2是p1淺層copy,但IdInfo是共用建構子
Person p2 = p1.ShallowCopy();
// 當然一開始都一樣
// p1 instance: Name: Sam, Age: 42, Value: 6565
// p2 instance: Name: Sam, Age: 42, Value: 6565
// 後來p1改了他的資料,但只有IdInfo影響到p2
// 因為p1一開始是使用new IdInfo,所以兩個人的IdInfo指向同一個reference
p1.Age = 32;
p1.Name = "Frank";
p1.IdInfo.IdNumber = 7878;
// p1 instance: Name: Frank, Age: 32, Value: 7878
// p2 instance: Name: Sam, Age: 42, Value: 7878
// p3是p1的深層copy
// 且p3的IdInfo又指向了新的reference
// 所以p1的改變除了Name, Age甚至是IdInfo完全不影響p3
Person p3 = p1.DeepCopy();
p1.Name = "George";
p1.Age = 39;
p1.IdInfo.IdNumber = 8641;
// p1 instance: Name: George, Age: 39, Value: 8641
// p3 instance: Name: Frank, Age: 32, Value: 7878
//---------------------------------------------
var a = new CopyObj("Lance");
Console.WriteLine(a.name); // Lance
var b = (CopyObj) a;
b.name = "Frank named by b";
Console.WriteLine(a.name); // Frank named by b
Console.WriteLine(b.name); // Frank named by b
// c的改變不影響b、a
var c = (CopyObj) b.Copy();
c.name = "Andy";
b.text = "Change from object b";
// a只影響到b
a.text = "Change from object a";
Console.WriteLine(a.name); // Frank named by b
Console.WriteLine(b.name); // Frank named by b
Console.WriteLine(c.name); // Andy
Console.WriteLine(b.text); // Change from object a
Console.WriteLine(c.text); // Change from object b
}
}
}
```
## 惡補區
:::warning
### public / private
* `public` 方案範圍
> can be accessed by any other code in the same `assembly` or another assembly that references it
>[color=transparent]
* `internal` 專案/命名空間範圍
> can be accessed only by code in the same `assembly`.[color=transparent]
* `private` class{ }之中
> can only be accessed by code in the same `class` or `struct`.
> [color=transparent]
* `protected` 不限定同一個命名空間,只要是繼承關係
> 只有在存取是透過 `衍生類別` 類型進行時,才可以存取衍生類別中屬於基底類別的受保護成員。[color=transparent]
* `protected internal` protected + 同一個命名空間類別,不需要繼承關係
> can be accessed by any code in the same assembly, or by any derived class in another assembly.[color=transparent]
:::
:::success
### partial
parital keyword be appended to both `public` and `private` classes. In a partial public class you'd be able to add functionalities to it in multiple source files, in a partial private class you'd be able to add functionalities to it within the same class.
```csharp
public class MyPublicClass
{
private partial class MyPrivateClass
{
int a;
int b;
}
private partial class MyPrivateClass
{
int c;
int d;
}
}
```
Now the last case , in a partial public class having a partial private class you can add functionality to both in multiple source files.
:::