1. 程式人生 > >map的鍵使用自定義結構體

map的鍵使用自定義結構體

背景:

map的定義

template<class Key, class T, class Pred = less<Key>, class A = allocator<T> >

可見,map的定義是一個模板類,模板引數為Key,T,Pred,A,各引數的含義如下:

Key---------鍵

T------------值

Pred--------map用於比較鍵的類,這個類必須過載()操作符,在其中定義比較操作..(雖然比較怪,不是過載大於小於號,但的確是這樣定義的)

A------------記憶體分配

注:由於map是採用了紅黑樹,而紅黑樹在操作節點時都需要依賴於比較節點間的大小,所以鍵採用自定義結構體的條件就是得讓系統可以對其進行比較.可以通過兩種方法提供這種功能:

1. 為結構體過載<操作符

2. 不需要為結構體過載<操作符.但需要提供一個Pred類,且該類提供了operator()過載.實際上通過class Pred = less<Key>可以看出,map預設使用系統提供的less類.

以下為兩種方案的例子:

1.為自定義型別過載operator<,map的第三個引數為預設仿函式less<key>。
例子:

  1. #include <iostream>
  2. #include <map>
  3. #include <string>
  4. using   namespace  std;
  5. class  test
  6. {
  7. public :
  8.      bool  operator<( const  test& a) const ;
  9. //private:
  10.      int  nA;
  11.      int  nB;
  12. };
  13. bool  test::operator<( const  test& a) const
  14. {
  15.      if ( this ->nA < a.nA)
  16.          return   true ;
  17.      else
  18.     {
  19.          if ( this ->nA == a.nA &&  this
    ->nB < a.nB)
  20.              return   true ;
  21.          else
  22.              return   false ;
  23.     }
  24. }
  25. int  main()
  26. {
  27.     map<test, string> myTestDemo;
  28.     test tA;
  29.     tA.nA = 1;
  30.     tA.nB = 1;
  31.     test tB;
  32.     tB.nA = 1;
  33.     tB.nB = 2;
  34.     myTestDemo.insert(pair<test, string>(tA,  "first!" ));
  35.     myTestDemo.insert(pair<test, string>(tB,  "second!" ));
  36.     map<test, string>::iterator myItr = myTestDemo.begin();
  37.     cout <<  "itr begin test nA:"  << myItr->first.nA << endl;
  38.     cout <<  "itr begin test nB:"  << myItr->first.nB << endl;
  39.     cout <<  "itr begin test string:"  << myItr->second << endl;
  40.      return  1;
  41. }

特別注意: operator < 函式的詳細內容,一定要滿足strict weakly ordering,不能單純的返回false或true

可以參考:http://www.softwelt.com/Know/KnowDetail-113762.html

2.不使用map的第三個引數為預設仿函式less<key>,自己編寫一個比較仿函式。

  1. #include <iostream>
  2. #include <map>
  3. using   namespace  std;
  4. struct  keyOfMap
  5. {
  6.      int  firstOfKey;
  7.      int  secondOfKey;
  8. };
  9. struct  myMapFunctor
  10. {
  11.      bool  operator()( const  keyOfMap& k1,  const  keyOfMap& k2)  const
  12.     {
  13.          if (k1.firstOfKey < k2.firstOfKey)
  14.              return   true ;
  15.          else
  16.              return   false ;
  17.     }
  18. };
  19. int  main()
  20. {
  21.     map<keyOfMap, string, myMapFunctor> test;
  22.     keyOfMap temp1;
  23.     keyOfMap temp2;
  24.     temp1.firstOfKey = 1;
  25.     temp1.secondOfKey = 1;
  26.     temp2.firstOfKey = 2;
  27.     temp2.secondOfKey = 2;
  28.     test.insert(make_pair<keyOfMap, string>(temp1,  "first" ));
  29.     test.insert(make_pair<keyOfMap, string>(temp2,  "second" ));
  30.     map<keyOfMap, string, myMapFunctor>::iterator begin = test.begin();
  31.     cout << begin->first.firstOfKey << begin->first.secondOfKey << begin->second << endl;
  32.      return  1;
注: 以上所述同樣適用於multimap 另,只要有了上述實現,map也可以使用find函數了,不需要過載==

相關推薦

map使用定義結構

背景: map的定義 template<class Key, class T, class Pred = less<Key>, class A = allocator<T> > 可見,map的定義是一個模板類,模板引數為Key,

定義結構做為map裡面的key的寫法

其中一種寫法: struct hook_info { string lib_name; string fun_name; int param_count; bool bIATHook; hook_info(char *lib

定義結構的對齊問題

一、跨平臺通用資料型別 之前的一篇部落格Linux資料型別(通用移植),已經自定義嘗試解決了資料通用型別問題。 這裡通過原始碼進行分析,利用原始碼進行解決問題。在<stdint.h>中我們發現: typedef signed char int8_t; typedef

定義結構及初始化

自定義結構體及初始化,以及標頭檔案先宣告巨集,然後宣告結構體 <pre name="code" class="cpp">/********************** macro definition **********************/ #ifndef CVALGO_

C++ 定義結構的Priority Queue

比較函式return true 意味著排序需要交換。   #include <iostream> #include <queue> #include <vector> #include <algorithm> using namespace

利用qt 訊號槽傳遞定義結構--藉助QVariant

在前面的部落格裡,我介紹了利用Q_DECLARE_METATYPE和qRegsterMetaType來傳遞自定義的結構體。但是這樣做有個缺點:qRegisterMetaType()只能在main()函式裡才能發揮作用。https://blog.csdn.net/Kelvin_Yan/article/

QT訊號槽傳遞定義結構

QT的訊號槽可以傳遞int, short, double等c語言的常用型別的變數,也可以傳遞如QImage之類的QT支援 的型別。但是如何傳遞一個程式設計師自定義的結構體? 1)在定義結構體之後,要呼叫Q_DECLARE_METATYPE,向QT宣告這個結構體 2)在main.cpp 中,用

[UE4]定義結構、類、資料表

自定義資料表: #pragma once #include "CoreMinimal.h" #include "Engine/UserDefinedStruct.h" #include "Components/CanvasPanel.h" #include "Blueprint/UserW

[UE4]定義結構、類、數據表

png table 小地圖 比例 pub 地圖 sse 面板 gpa 自定義數據表: #pragma once #include "CoreMinimal.h" #include "Engine/UserDefinedStruct.h" #include "

Solidity學習::(10)定義結構

自定義結構體 定義  跟其他語言類似 //學生 struct Student{ string name; int num; } //班級 struct Class{ string clsName; //學生的列表

Linux核心dev_set_drvdata()和dev_get_drvdata()儲存定義結構用法

定義位置:kernel/msm-3.18/include/linux/device.h static inline void dev_set_drvdata(struct device *dev, void *data){ dev->driver_data = data; } stat

Solidity的定義結構深入詳解

一.結構體定義   結構體,Solidity中的自定義型別。我們可以使用Solidity的關鍵字struct來進行自定義。結構體內可以包含字串,整型等基本資料型別,以及陣列,對映,結構體等複雜型別。陣列,對映,結構體也支援自定義的結構體。我們來看一個自定義結構體的定義: pragma solidit

C/C++動態定義結構陣列例項鍛鍊-學生成績排序

/************************************************************************/ /* 本程式是對動態記憶體、動態陣列、結構體、函式的綜合應用。 */ /***********************

QT:用QSet儲存定義結構的問題

前幾天要用QSet作為儲存一個自定義的結構體(就像下面這個程式一樣),結果死活不成功。。。後來還跑到論壇上問人了,丟臉丟大了。。。 事先說明:以下這個例子是錯誤的 [cpp] view plaincopyprint? #include <QtCore> struct node

c++ map 使用定義結構做關鍵字

map在STL中的定義 template <class Key, class T, class Compare = less<Key>, class Alloc = alloc>  第一個引數Key是關鍵字型別 第二個引數T是值型別 第三個引數Com

iOS 定義結構結構轉換成物件

1、新建一個頭檔案,如下程式碼: #ifndef Header_h #define Header_h struct MyStruce{     char *name;//(指標形式)     char *address;     CGFloat age;

關於Go語言,定義結構標籤的一個妙用.

在Go中首字母大小寫,決定著這此變數是否能被外部呼叫, 例如:在使用標準庫的json編碼自定一的結構的時候: <pre style="margin-top: 0px; margin-bottom: 0px;"><span style=" font-weig

再談:定義結構的對齊問題之__attribute__ ((packed))方法

問題來源:     我們在程式開發過程中往往會遇到這樣的問題:以某種資料格式寫入,再以此格式讀出,特別是socket通訊中,通常會遇到資料錯位問題,這就是資料結構的對齊的問題。為了讓我們的資料結構以

使用STL去除std::vector定義結構重複項

最近搞了一個小東西要去除一個vector中重複的項。是這樣的:我用組播搜尋裝置,得到裝置IP資訊、版本號資訊,等,但有時會接收到多個相同IP裝置的資訊,因此要過濾掉重複的IP。我使用vector儲存每臺裝置資訊,包括IP、版本號,因此需要使用結構體。另外,要對這些裝置IP進

定義結構排序

#include <cstdio> #include <iostream> #include <iterator> #include <cstring>