C#面向對象核心-其它

来源:https://www.cnblogs.com/tanyuyang/archive/2023/03/28/17266793.html
-Advertisement-
Play Games

其他 1 命名空間 命名空間用來組織和重用代碼的,命名空間就像一個工具包,類就像工具。 1.1 使用 namespace MyGame { class GameObject { } } namespace MyGame//命名空間可以分開寫 { class Player : GameObject { ...


其他

1 命名空間

命名空間用來組織和重用代碼的,命名空間就像一個工具包,類就像工具。

1.1 使用

namespace MyGame
{
    class GameObject
    {

    }
}

namespace MyGame//命名空間可以分開寫
{
    class Player : GameObject
    {

    }
}

1.2 不同命名空間中相互使用

使用 using 命名空間名命名空間名.內容 來使用所需命名空間的內容。

1.3 不同命名空間中允許有同名類

此時要使用同名類,必須指明出處的使用方法:命名空間名.類名

namespace MyGame2
{
    class GameObject//不同命名空間的同名類
    {

    }
}

1.4 命名空間可以包裹命名空間

表示工具包裡面的小包,若要使用小包,必須using到小包,如:using MyGame.UI,只using MyGame是無法使用UI的。

namespace MyGame
{
    namespace UI
    {
        class Image
        {

        }
    }

    namespace Game
    {
        class Image
        {

        }
    }
}

//Main
GameObject g = new GameObject();
MyGame.UI.Image i = new MyGame.UI.Image();

1.5 關於修飾類的訪問修飾符

  • public 公有類,命名空間中的類預設為public
  • internal 內部類,只能在該工程的程式集中使用
  • abstract 抽象類
  • sealed 密封類
  • partial 分部類

2 object 中的方法

2.1 靜態方法

Equals:判斷兩個對象是否相等,返回true或false
最終的判斷權由左側對象決定,不管是值類型還是引用類型都按照左側對象的規則來比較

ReferenceEquals:判斷兩個對象是否是相同的引用,用來比較引用類型的對象
值類型對象的返回值始終是false

class Test
{

}

//Main
Console.WriteLine(Object.Equals(1, 1));//值類型

Test t1 = new Test();
Test t2 = new Test();
Test t3 = t1;
Console.WriteLine(Object.Equals(t1,t2));//引用類型
Console.WriteLine(Object.Equals(t1,t3));

Console.WriteLine(ReferenceEquals(1,1));//object是所有類型的基類,直接用靜態方法也可以
Console.WriteLine(Object.ReferenceEquals(t1,t3));

/*
輸出:
True
False
True
False
True
*/

2.2 成員方法

GetType:獲取對象運行時的Type類型
通過Type結合反射相關知識點可以做很多關於對象的操作

MemberwiseClone:獲取對象的淺拷貝對象
返回一個新的對象,新對象的引用變數會和老對象一致

2.3 虛方法

虛方法可以 override 重寫。

Equals:預設實現還是比較兩者是否為同一個引用,相當於ReferenceEquals
微軟在所有值類型的基類system.ValueType中重寫了該方法,用來比較值相等。我們也可以重寫該方法,定義自己的比較相等的規則

GetHashCode:獲取對象的哈希碼(一種通過演算法算出的表示對象的唯一編碼,不同對象哈希碼有可能一樣,具體值根據哈希演算法決定)
我們可以通過重寫該函數來自己定義對象的哈希碼演算法,正常情況下,我們使用的極少,基本不用

ToString:返回當前對象代表的字元串
調用列印方法Console.WriteLine()時,預設使用的就是對象的Tostring方法後列印出來的內容

3 string

3.1 字元串指定位置獲取

//字元串本質是char數組
string str = "abc";
Console.WriteLine(str[0]);//a
//轉為char數組
char[] chars = str.ToCharArray();
Console.WriteLine(chars[1]);//b

3.2 字元串拼接

str = string.Format("{0}{1}", 1, 23);
Console.WriteLine(str);//123

3.3 正向查找字元串的第一個出現位置

str = "abccdefg";
Console.WriteLine(str.IndexOf("c"));//2 返回下標,從0開始
Console.WriteLine(str.IndexOf("h"));//未找到則返回-1

3.4 反向查找字元串的第一個出現位置

Console.WriteLine(str.LastIndexOf("c"));//3

3.5 移除指定位置及之後的字元

  • string 是特殊的引用,特殊的地方在於會在堆中重新分配空間,因此它變我不變,需要賦值來改變內容
str = "abcdefghi";
str.Remove(6);//返回移除後的字元串,並沒有改變原字元串
Console.WriteLine(str);//abcdefghi
str = str.Remove(6);
Console.WriteLine(str);//abcdef

str = str.Remove(4, 2);//兩個參數,分別表示開始位置和字元個數
Console.WriteLine(str);//abcd

3.6 替換指定字元串

str = "abcdefg";
str.Replace("a", "b");
Console.WriteLine(str);//abcdefg
str = str.Replace("a", "b");
Console.WriteLine(str);//bbcdefg

3.7 大小寫轉換

str = "abcdefg";
str.ToUpper();
Console.WriteLine(str);//abcdefg
str = str.ToUpper();
Console.WriteLine(str);//ABCDEFG
str = str.ToLower();
Console.WriteLine(str);//abcdefg

3.8 字元串截取

str = "abcdefg";
//截取指定位置及之後的字元串
str.Substring(2);
Console.WriteLine(str);//abcdefg
str = str.Substring(2);
Console.WriteLine(str);//cdefg

//截取指定位置及之後3個字元
str = str.Substring(2, 3);
Console.WriteLine(str);//efg

3.9 字元串切割

str = "1,2,3,4,5,6,7,8";
string[] strs = str.Split(',');//基於傳入參數將字元串拆分成多個子字元串
foreach(string s in strs)
{
    Console.WriteLine(s);//1 2 3 4 5 6 7 8
}

4 stringBulider

4.1 基本概念

  • 在頻繁對string重新賦值時會產生記憶體垃圾,C#提供stringBulider用於處理字元串的公共類,可以提升性能
  • 在使用 StringBuilder 類時,每次都會對 StringBuilder 對象本身進行操作,而不是生成新的對象,如果需要經常對字元串進行修改推薦使用
  • 使用前需要 using System.Text
StringBuilder str = new StringBuilder("123456");
Console.WriteLine(str);

4.2 容量

  • StringBuilder 的容量一般比字元串多,每次往字元串里增加時,會存在空的容量裡面
  • 如果插入後大於容量,則會自動申請新的記憶體空間,容量大小*2(看記憶體機制),原本的字元串會變成垃圾
Console.WriteLine(str.Length);//6
Console.WriteLine(str.Capacity);//16
//增
str.Append("789");
Console.WriteLine(str);//123456789
Console.WriteLine(str.Length);//9
Console.WriteLine(str.Capacity);//16
//插入
str.Insert(0, "123456789");
Console.WriteLine(str);//123456789123456789
Console.WriteLine(str.Length);//18
Console.WriteLine(str.Capacity);//25 自動申請新的記憶體空間
//刪
str.Remove(0, 3);
Console.WriteLine(str);//456789123456789
//查
Console.WriteLine(str[0]);//4
//改
str[0] = 'X';
Console.WriteLine(str);//X56789123456789
//替換
str.Replace("X", "T");
Console.WriteLine(str);//X56789123456789
//清空
str.Clear();
Console.WriteLine(str);//空

//重新賦值 StringBuilder,這種方法可以避免產生記憶體垃圾
str.Clear();
str.Append("987654321");
Console.WriteLine(str);//987654321

//判斷相等
if (str.Equals("987654321"))//不相等
{
    Console.WriteLine("相等");
}
else
{
    Console.WriteLine("不相等");
}

5 結構體和類的區別

5.1 區別概述

結構體和類最大的區別是在存儲空間上的,因為結構體是值,類是引用,因此他們的存儲位置一個在棧上,一個在堆上。

  • 結構體和類在使用上很類似,結構體甚至可以用面向對象的思想來形容一類對象。
  • 結構體具備著面向對象思想中封裝的特性,但是它不具備繼承和多態的特性,因此大大減少了它的使用頻率。
  • 由於結構體不具備繼承的特性,所以它不能夠使用protected保護訪問修飾符。

5.2 細節區別

  1. 結構體是值類型,類是引用類型
  2. 結構體存在棧中,類存在堆中
  3. 結構體成員不能使用protected訪問修飾符,而類可以
  4. 結構體成員變數申明不能指定初始值,而類可以
  5. 結構體不能申明無參的構造函數,而類可以
  6. 結構體申明有參構造函數後,無參構造不會被頂掉
  7. 結構體不能申明析構函數,而類可以
  8. 結構體不能被繼承,而類可以
  9. 結構體需要在構造函數中初始化所有成員變數,而類隨意
  10. 結構體不能被靜static修飾 (不存在靜態結構體) ,而類可以
  11. 結構體不能在自己內部申明和自已一樣的結構體變數,而類可以

5.3 結構體的特別之處

結構體可以繼承介面,因為介面是行為的抽象。

5.4 如何選擇結構體和類

  • 想要用繼承和多態時,直接淘汰結構體,比如玩家、怪物等
  • 對象時數據集合時,優先考慮結構體,比如位置、坐標等
  • 從值類型和引用類型賦值時的區別上去考慮,比如經常被賦值傳遞的對象,並且改變賦值對象,原對象不想跟著變化時,就用結構體。比如坐標、向量、旋轉等等

6 抽象類和介面的區別

6.1 回顧

抽象類和抽象方法:

  • abstract修飾的類和方法
  • 抽象類 不能實例化
  • 抽象方法只能在抽象類中申明 是個純虛方法 必須在子類中實現

介面:

  • interface 自定義類型
  • 是行為的抽象
  • 不包含成員變數
  • 僅包含方法、屬性、索引器、事件,成員都不能實現,建議不寫訪問修飾符,預設public

6.2 相同點

  1. 都可以被繼承
  2. 都不能直接實例化
  3. 都可以包含方法申明
  4. 子類必須實現未實現的方法
  5. 都遵循里氏替換原則

6.3 不同點

  1. 抽象類中可以有構造函數;介面中不能
  2. 抽象類只能被單一繼承,介面可以被繼承多個
  3. 抽象類中可以有成員變數;介面中不能
  4. 抽象類中可以申明成員方法,虛方法,抽象方法,靜態方法;介面中只能申明沒有實現的抽象方法
  5. 抽象類方法可以使用訪問修飾符;介面中建議不寫,預設public

6.4 如何選擇抽象類和介面

  • 表示對象的用抽象類,表示行為拓展的用介面
  • 不同對象擁有的共同行為,我們往往可以使用介面來實現
  • 舉個例子:動物是一類對象,我們自然會選擇抽象類;而飛翔是一個行為,我們自然會選擇介面

您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 什麼是Base64 Base64編碼是將字元串以每3個8比特(bit)的位元組子序列拆分成4個6比特(bit)的位元組(6比特有效位元組,最左邊兩個永遠為0,其實也是8比特的位元組)子序列,再將得到的子序列查找Base64的編碼索引表,得到對應的字元拼接成新的字元串的一種編碼方式。 每個3位8比特數據拆分成 ...
  • 藍橋杯【答疑】 題目描述 分析 這是一個貪心演算法,要所得的時刻之和最小,而且下一個同學需要等上一個同學結束以後才能進行,因此需要對所耗總時間進行有小到大的排序,總時間相同的同學則對前兩步時間之和有小到大進行排序,最後算出時間之和即可。 代碼 import java.util.Arrays; impo ...
  • 附件用的fastdf上傳和下載的, 本地開發時就沒考慮過多文件上傳就會有併發的問題,比如多個只上傳成功了一個或者上傳了但是文檔內容缺失了,變成0位元組。 呵。。都是一次難忘的經歷。 經過本地模擬大批量的上傳下載, 發現fastdf是在啟動時就初始化了tracker和stroge, 每次調用過他的介面後 ...
  • 一、Jx9 虛擬機的生命周期 載入 Jx9 腳本 jx9_compile() 或 jx9_compile_file(),載入編譯成功後,Jx9 引擎將自動創建一個實例 (jx9_vm) 並且返回指向此虛擬機的指針用於後續調用。 如載入編譯 Jx9 腳本時出現問題,也就是編譯時出錯,可調用jx9_co ...
  • 生產環境,一個簡單的事務方法,提交失敗,報 Global lock wait timeout 偽代碼如下: @GlobalTransactional(rollbackFor = Exception.class,timeoutMills = 30000,lockRetryInternal=3000,l ...
  • PowerPlume是PowerBuilder深度創新的擴展開發框架(免費商用)。 它的三個主要特色是一、原創功能;二、零改動相容(非侵入性);三、極簡介面設計。 ...
  • 記錄人生第一次重裝系統之後的數據恢復過程,包括桌面恢復、常用軟體下載和屬性修改、vscode插件、zotero數據恢復、onenote筆記數據恢復,讓重裝系統的你不用慌。 ...
  • 發文原因 很多初學者都使用 cargo new [project_name] 來創建項目,並直接在 main.rs 文件中實現所有功能。 這樣是不合理的,並不符合我們 cargo 的開發規範。 下麵將簡單的介紹一下 rust project 中的文件結構。 cargo new [project_na ...
一周排行
    -Advertisement-
    Play Games
  • Timer是什麼 Timer 是一種用於創建定期粒度行為的機制。 與標準的 .NET System.Threading.Timer 類相似,Orleans 的 Timer 允許在一段時間後執行特定的操作,或者在特定的時間間隔內重覆執行操作。 它在分散式系統中具有重要作用,特別是在處理需要周期性執行的 ...
  • 前言 相信很多做WPF開發的小伙伴都遇到過表格類的需求,雖然現有的Grid控制項也能實現,但是使用起來的體驗感並不好,比如要實現一個Excel中的表格效果,估計你能想到的第一個方法就是套Border控制項,用這種方法你需要控制每個Border的邊框,並且在一堆Bordr中找到Grid.Row,Grid. ...
  • .NET C#程式啟動閃退,目錄導致的問題 這是第2次踩這個坑了,很小的編程細節,容易忽略,所以寫個博客,分享給大家。 1.第一次坑:是windows 系統把程式運行成服務,找不到配置文件,原因是以服務運行它的工作目錄是在C:\Windows\System32 2.本次坑:WPF桌面程式通過註冊表設 ...
  • 在分散式系統中,數據的持久化是至關重要的一環。 Orleans 7 引入了強大的持久化功能,使得在分散式環境下管理數據變得更加輕鬆和可靠。 本文將介紹什麼是 Orleans 7 的持久化,如何設置它以及相應的代碼示例。 什麼是 Orleans 7 的持久化? Orleans 7 的持久化是指將 Or ...
  • 前言 .NET Feature Management 是一個用於管理應用程式功能的庫,它可以幫助開發人員在應用程式中輕鬆地添加、移除和管理功能。使用 Feature Management,開發人員可以根據不同用戶、環境或其他條件來動態地控制應用程式中的功能。這使得開發人員可以更靈活地管理應用程式的功 ...
  • 在 WPF 應用程式中,拖放操作是實現用戶交互的重要組成部分。通過拖放操作,用戶可以輕鬆地將數據從一個位置移動到另一個位置,或者將控制項從一個容器移動到另一個容器。然而,WPF 中預設的拖放操作可能並不是那麼好用。為瞭解決這個問題,我們可以自定義一個 Panel 來實現更簡單的拖拽操作。 自定義 Pa ...
  • 在實際使用中,由於涉及到不同編程語言之間互相調用,導致C++ 中的OpenCV與C#中的OpenCvSharp 圖像數據在不同編程語言之間難以有效傳遞。在本文中我們將結合OpenCvSharp源碼實現原理,探究兩種數據之間的通信方式。 ...
  • 一、前言 這是一篇搭建許可權管理系統的系列文章。 隨著網路的發展,信息安全對應任何企業來說都越發的重要,而本系列文章將和大家一起一步一步搭建一個全新的許可權管理系統。 說明:由於搭建一個全新的項目過於繁瑣,所有作者將挑選核心代碼和核心思路進行分享。 二、技術選擇 三、開始設計 1、自主搭建vue前端和. ...
  • Csharper中的表達式樹 這節課來瞭解一下表示式樹是什麼? 在C#中,表達式樹是一種數據結構,它可以表示一些代碼塊,如Lambda表達式或查詢表達式。表達式樹使你能夠查看和操作數據,就像你可以查看和操作代碼一樣。它們通常用於創建動態查詢和解析表達式。 一、認識表達式樹 為什麼要這樣說?它和委托有 ...
  • 在使用Django等框架來操作MySQL時,實際上底層還是通過Python來操作的,首先需要安裝一個驅動程式,在Python3中,驅動程式有多種選擇,比如有pymysql以及mysqlclient等。使用pip命令安裝mysqlclient失敗應如何解決? 安裝的python版本說明 機器同時安裝了 ...