0
  • 聊天消息
  • 系統(tǒng)消息
  • 評論與回復(fù)
登錄后你可以
  • 下載海量資料
  • 學(xué)習(xí)在線課程
  • 觀看技術(shù)視頻
  • 寫文章/發(fā)帖/加入社區(qū)
會(huì)員中心
創(chuàng)作中心

完善資料讓更多小伙伴認(rèn)識你,還能領(lǐng)取20積分哦,立即完善>

3天內(nèi)不再提示

使用C++ sort函數(shù)對vector進(jìn)行自定義排序

冬至配餃子 ? 來源:鳴鳴鑼的小屋 ? 作者:Maxwell Luo ? 2023-07-22 10:12 ? 次閱讀

>>> 背景

今天在學(xué)一些C++ STL容器,看到sort函數(shù)允許自定義排序規(guī)則,小小地實(shí)操了一下。

>>> 內(nèi)容

vector

在正式開始使用sort之前,我們先鋪墊一些關(guān)于vector容器的內(nèi)容,以及自定義標(biāo)準(zhǔn)輸出流,為我們后面的探索鋪墊一下。

vector容器是一種動(dòng)長的模板容器,需要 # include 。定義一個(gè)vector對象需要指定元素類型,這個(gè)類型可以是基礎(chǔ)類型,結(jié)構(gòu)體,自定義類型和vector類型自身(達(dá)到嵌套多維vector的目的)。

如下面代碼所示,創(chuàng)建了一個(gè)元素類型為 int 的vector對象,并使用列表進(jìn)行初始化。除此之外,還可以使用assign方法進(jìn)行快速初始化。

// 元素為 1,2,3,4,5
vector< int > vec(5) = {1, 2, 3, 4, 5}; 
// 元素為 1,1,1,1,1
vector< int > vec(5);
vec.assign(1, 5)

還可以創(chuàng)建二維容器,如下所示。注意到此時(shí)的模板元素類型參數(shù)變成了 vector< int >。

vector< vector< int >> vec2 = {vec, vec, vec, vec, vec};

為了能夠方便地打印出vector對象的元素,需要自定義一些輸出函數(shù)。這里分別對一維和二維的vector容器定義了打印函數(shù)(模板)。

template < typename T >
void print1vec(const vector< T >& v) {
    auto iter = v.begin();
    while (iter != v.end()) {
        cout < < *iter < < " ";
        iter++;
    }
    cout < < endl;
}


template < typename T >
void print2vec(const vector< vector< T >>& v) {
    auto iter = v.begin();
    while (iter != v.end()) {
        print1vec(*iter);
        iter++;
    }
    cout < < endl;
}

為了讓輸出更加優(yōu)雅和方便,可以重載<<運(yùn)算符,如下所示。

template < typename T >
ostream& operator< const vector< T >& v) {
    auto iter = v.begin();
    while (iter != v.end()) {
        os < < *iter < < " ";
        iter++;
    }
    os < < endl;
    return os;
};


template < typename T >
ostream& operator< const vector< vector< T >>& v) {
    auto iter = v.begin();
    while (iter != v.end()) {
        os < < *iter;
        iter++;
    }
    os < < endl;
    return os;
};

sort

使用sort需要 #include 。sort函數(shù)最簡單的用法如下。第一個(gè)參數(shù)傳入容器的頭地址(或指向頭元素的迭代器),第二個(gè)參數(shù)傳入容器的尾地址(或指向尾元素的迭代器)的下一個(gè)位置(前閉后開的區(qū)間)。

int arr[5] = {1, 3, 5, 2, 4};
    sort(arr, arr + 5);
    for (int i = 0; i < 5; ++i)
        cout < < arr[i] < < " ";
>> 1 2 3 4 5

還可以傳入第3個(gè)參數(shù),即排序判據(jù)。該判據(jù)由一個(gè)函數(shù)對象來實(shí)現(xiàn),有兩個(gè)參數(shù),返回bool值。sort在排序時(shí),會(huì)依次把兩個(gè)元素傳入給該函數(shù)對象進(jìn)行判斷,如果返回值為true,那么就會(huì)把第一個(gè)參數(shù)代表的元素放到隊(duì)列中靠前的位置。

因此,可以傳入判據(jù)函數(shù)來快速實(shí)現(xiàn)降序排序(這里使用了lambda表達(dá)式)。如下所示。

int arr[5] = {1, 3, 5, 2, 4};
sort(arr, arr + 5,
        [](int a, int b) {
            return a > b;
        });
    for (int i = 0; i < 5; ++i)
        cout < < arr[i] < < " ";

5 4 3 2 1

判據(jù)函數(shù)給了用戶自己決定元素比較關(guān)系的途徑,尤其是對一些非基礎(chǔ)類型的數(shù)據(jù)(如結(jié)構(gòu)、類)可以方便地進(jìn)行排序。

下面就創(chuàng)建了一個(gè)結(jié)構(gòu)體 ,并規(guī)定如果該結(jié)構(gòu)體的兩個(gè)成員的平方和越小,排序越靠前。

struct Point {
    int x; 
    int y;
};


ostream& operator< const Point& p) {
    os < < "(" < < p.x < < ", " < < p.y < < ")";
    return os;
};
vector< Point > vec3;
Point p1 = {1, 1};
Point p2 = {-3, -3};
Point p3 = {2, 2};
vec3.push_back(p1);
vec3.push_back(p2);
vec3.push_back(p3);
cout < < "vec3: " < < endl;
cout < < vec3;
sort(vec3.begin(), vec3.end(),
    [](Point a, Point b){
        return a.x * a.x +  a.y * a.y < b.x * b.x +  b.y * b.y;
    });
cout < < vec3;
> > vec3:
(1, 1) (-3, -3) (2, 2)
(1, 1) (2, 2) (-3, -3)
聲明:本文內(nèi)容及配圖由入駐作者撰寫或者入駐合作網(wǎng)站授權(quán)轉(zhuǎn)載。文章觀點(diǎn)僅代表作者本人,不代表電子發(fā)燒友網(wǎng)立場。文章及其配圖僅供工程師學(xué)習(xí)之用,如有內(nèi)容侵權(quán)或者其他違規(guī)問題,請聯(lián)系本站處理。 舉報(bào)投訴
  • C++語言
    +關(guān)注

    關(guān)注

    0

    文章

    147

    瀏覽量

    6931
  • STL算法
    +關(guān)注

    關(guān)注

    0

    文章

    6

    瀏覽量

    5355
  • 迭代器
    +關(guān)注

    關(guān)注

    0

    文章

    43

    瀏覽量

    4289
收藏 人收藏

    評論

    相關(guān)推薦

    OpenHarmony自定義組件

    **可通過@Builder裝飾器進(jìn)行描述,該裝飾器可以修飾一個(gè)函數(shù),此函數(shù)可以在build函數(shù)之外聲明,并在build函數(shù)中或其他@Buil
    的頭像 發(fā)表于 12-08 12:26 ?1702次閱讀

    c++vector容器

    ,向量是一個(gè)能夠存放任意類型的動(dòng)態(tài)數(shù)組。 1.1 vector和普通數(shù)組區(qū)別 ? ? 普通數(shù)組是靜態(tài)的,在初始化是就確定空間大小,不支持動(dòng)態(tài)擴(kuò)展; ? ? vector則可以看做是一個(gè)動(dòng)態(tài)的數(shù)組,可以存放任意數(shù)據(jù)(基本數(shù)據(jù)類型和自定義
    的頭像 發(fā)表于 07-13 19:36 ?1284次閱讀
    <b class='flag-5'>c++</b>之<b class='flag-5'>vector</b>容器

    CC1310不調(diào)用庫函數(shù),怎么自定義ISR?

    vector=1__interrupt void TRAP_IRQHandler(void){}來自定義一個(gè)中斷服務(wù)處理函數(shù)ISR?
    發(fā)表于 03-09 11:05

    matlab自定義函數(shù)調(diào)用的方法

    matlab自定義函數(shù)調(diào)用的方法 命令文件/函數(shù)文件+ 函數(shù)文件 - 多
    發(fā)表于 11-29 13:14 ?88次下載

    自定義函數(shù)測試學(xué)習(xí)工程

    自定義函數(shù)測試學(xué)習(xí)工程
    發(fā)表于 07-01 16:37 ?5次下載

    制作和使用自定義C庫文件

    制作和使用自定義C庫文件 目標(biāo) 1.制作一個(gè)庫文件libGetMax.a ,其中包含一個(gè)外部函數(shù)GetMax ?!?b class='flag-5'>函數(shù)GetMax的作用是判斷
    發(fā)表于 01-16 11:58 ?1265次閱讀

    1602自定義字符

    1602液晶能夠顯示自定義字符,能夠根據(jù)讀者的具體情況顯示自定義字符。
    發(fā)表于 01-20 15:43 ?1次下載

    C#教程之自定義屏保

    C#教程之自定義屏保,很好的C#資料,快來學(xué)習(xí)吧。
    發(fā)表于 04-20 09:59 ?7次下載

    C#教程之自定義水晶按鈕控件

    C#教程之自定義水晶按鈕控件,很好的C#資料,快來學(xué)習(xí)吧。
    發(fā)表于 04-20 10:50 ?5次下載

    C#教程之自定義動(dòng)畫鼠標(biāo)

    C#教程之自定義動(dòng)畫鼠標(biāo),很好的C#資料,快來學(xué)習(xí)吧。
    發(fā)表于 04-20 14:46 ?4次下載

    C#與STM32自定義通信協(xié)議

    C#與STM32自定義通信協(xié)議功能:1.可通過C#上位機(jī)對多臺STM32下位機(jī)進(jìn)行控制2.自定義上位機(jī)與下位機(jī)通信協(xié)議
    發(fā)表于 12-24 18:59 ?37次下載
    <b class='flag-5'>C</b>#與STM32<b class='flag-5'>自定義</b>通信協(xié)議

    自定義視圖組件教程案例

    自定義組件 1.自定義組件-particles(粒子效果) 2.自定義組件- pulse(脈沖button效果) 3.自定義組件-progress(progress效果) 4.
    發(fā)表于 04-08 10:48 ?14次下載

    如何自定義函數(shù)或局部腳本

    系統(tǒng)函數(shù)是所有隨 WinCC 一同提供的函數(shù)。系統(tǒng)函數(shù)可應(yīng)用在函數(shù)列表、用戶自定義函數(shù)或局部腳本
    的頭像 發(fā)表于 10-10 10:45 ?1317次閱讀

    labview超快自定義控件制作和普通自定義控件制作

    labview超快自定義控件制作和普通自定義控件制作
    發(fā)表于 08-21 10:32 ?11次下載

    sort函數(shù)python用法

    sort()函數(shù)是Python中的內(nèi)置函數(shù)之一,用于對可迭代對象進(jìn)行排序??傻鷮ο蟀斜?、元組和字符串等。
    的頭像 發(fā)表于 11-21 15:15 ?1046次閱讀