zoukankan      html  css  js  c++  java
  • 侯捷STL学习(二)--序列容器测试

    第六节:容器之分类和各种测试(四)

    • stack不提供iterator操作,破坏了容器的独特性,先进先出。

    使用容器multiset(允许元素重复)

    • 内部是红黑树,insert操作就保证了排好了序。
    • 标准库有个::find()函数,大家都可以用。容器本身也有一个c.find(),通过键值对查找非常快!
    • 测试
    #include <set>
    #include <stdexcept>
    #include <string>
    #include <cstdlib> //abort()
    #include <cstdio>  //snprintf()
    #include <iostream>
    #include <ctime> 
    namespace jj06
    {
    void test_multiset(long& value)
    {
    	cout << "
    test_multiset().......... 
    ";
    	
    multiset<string> c;  	
    char buf[10];		
    clock_t timeStart = clock();								
        for(long i=0; i< value; ++i)
        {
        	try {
        		snprintf(buf, 10, "%d", rand());
            	c.insert(string(buf));     				
    		}
    		catch(exception& p) {
    			cout << "i=" << i << " " << p.what() << endl;	
    			abort();
    		}
    	}
    	cout << "milli-seconds : " << (clock()-timeStart) << endl;	
    	cout << "multiset.size()= " << c.size() << endl;	
    	cout << "multiset.max_size()= " << c.max_size() << endl;	//214748364
    	
    string target = get_a_target_string();	
    	{
        timeStart = clock();
    auto pItem = find(c.begin(), c.end(), target);	//比 c.find(...) 慢很多	
    	cout << "std::find(), milli-seconds : " << (clock()-timeStart) << endl;		
    	if (pItem != c.end())
        	cout << "found, " << *pItem << endl;
      	else
        	cout << "not found! " << endl;	
     	}
     	
     	{
        timeStart = clock();		
    auto pItem = c.find(target);		//比 std::find(...) 快很多							
    	cout << "c.find(), milli-seconds : " << (clock()-timeStart) << endl;		 
    	if (pItem != c.end())
        	cout << "found, " << *pItem << endl;
      	else
        	cout << "not found! " << endl;	
     	}	
    	 
    	c.clear();
    	test_moveable(multiset<MyString>(),multiset<MyStrNoMove>(), value);	 						
    }															 
    }
    

    使用容器multimap(允许元素重复)

    • 内部是红黑树,key-value键值对。
    • multiset不可用[]做insertion
    • c.insert(pair<long,string>(i,buff))
    • (*pItem).second
    • 测试
    #include <map>
    #include <stdexcept>
    #include <string>
    #include <cstdlib> //abort()
    #include <cstdio>  //snprintf()
    #include <iostream>
    #include <ctime> 
    namespace jj07
    {
    void test_multimap(long& value)
    {
    	cout << "
    test_multimap().......... 
    ";
         
    multimap<long, string> c;  	
    char buf[10];
    			
    clock_t timeStart = clock();								
        for(long i=0; i< value; ++i)
        {
        	try {
        		snprintf(buf, 10, "%d", rand());
        		//multimap 不可使用 [] 做 insertion 
            	c.insert(pair<long,string>(i,buf));   						
    		}
    		catch(exception& p) {
    			cout << "i=" << i << " " << p.what() << endl;	
    			abort();
    		}
    	}
    	cout << "milli-seconds : " << (clock()-timeStart) << endl;	
    	cout << "multimap.size()= " << c.size() << endl;
    	cout << "multimap.max_size()= " << c.max_size() << endl;	//178956970	
    	
    long target = get_a_target_long();		
        timeStart = clock();		
    auto pItem = c.find(target);								
    	cout << "c.find(), milli-seconds : " << (clock()-timeStart) << endl;	 
    	if (pItem != c.end())
        	cout << "found, value=" << (*pItem).second << endl;
      	else
        	cout << "not found! " << endl;	  
    		
    	c.clear();		  					
    }															 
    }
    

    使用unordered_multiset容器

    • 使用hashtable使用分离链地址方法实现
    • gnu C之前的名称hash_multiset
    • unorder_multiset.bucket_count篮子的个数
    • load_factor,max_load_factor,max_bucket_count方法
    • 篮子后面的链表不能太长,元素的个数大于等于篮子的个数,就需要重新分配篮子的大小,重新进行插入元素
    • c.find()容器自身的find操作快很多
    • 测试
    #include <unordered_set>
    #include <stdexcept>
    #include <string>
    #include <cstdlib> //abort()
    #include <cstdio>  //snprintf()
    #include <iostream>
    #include <ctime> 
    namespace jj08
    {
    void test_unordered_multiset(long& value)
    {
    	cout << "
    test_unordered_multiset().......... 
    ";
         
    unordered_multiset<string> c;  	
    char buf[10];
    			
    clock_t timeStart = clock();								
        for(long i=0; i< value; ++i)
        {
        	try {
        		snprintf(buf, 10, "%d", rand());
            	c.insert(string(buf));   			  		
    		}
    		catch(exception& p) {
    			cout << "i=" << i << " " << p.what() << endl;	
    			abort();
    		}
    	}
    	cout << "milli-seconds : " << (clock()-timeStart) << endl;		
    	cout << "unordered_multiset.size()= " << c.size() << endl;
    	cout << "unordered_multiset.max_size()= " << c.max_size() << endl;	//357913941
    	cout << "unordered_multiset.bucket_count()= " << c.bucket_count() << endl;	
    	cout << "unordered_multiset.load_factor()= " << c.load_factor() << endl;	
    	cout << "unordered_multiset.max_load_factor()= " << c.max_load_factor() << endl;	
    	cout << "unordered_multiset.max_bucket_count()= " << c.max_bucket_count() << endl;				
      	for (unsigned i=0; i< 20; ++i) {
        	cout << "bucket #" << i << " has " << c.bucket_size(i) << " elements.
    ";
      	}					
    				
    string target = get_a_target_string();	
    	{
        timeStart = clock();
    auto pItem = find(c.begin(), c.end(), target);	//比 c.find(...) 慢很多	
    	cout << "std::find(), milli-seconds : " << (clock()-timeStart) << endl;	
    	if (pItem != c.end())
        	cout << "found, " << *pItem << endl;
      	else
        	cout << "not found! " << endl;	
     	}
     
     	{
        timeStart = clock();		
    auto pItem = c.find(target);		//比 std::find(...) 快很多							
    	cout << "c.find(), milli-seconds : " << (clock()-timeStart) << endl;	 
    	if (pItem != c.end())
        	cout << "found, " << *pItem << endl;
      	else
        	cout << "not found! " << endl;	
     	}		
    	 
        c.clear();
    	test_moveable(unordered_multiset<MyString>(),unordered_multiset<MyStrNoMove>(), value);		 	 							
    }													 
    }
    

    使用unordered_multimap容器

    • 测试
    #include <unordered_map>
    #include <stdexcept>
    #include <string>
    #include <cstdlib> //abort()
    #include <cstdio>  //snprintf()
    #include <iostream>
    #include <ctime> 
    namespace jj09
    {
    void test_unordered_multimap(long& value)
    {
    	cout << "
    test_unordered_multimap().......... 
    ";
         
    unordered_multimap<long, string> c;  	
    char buf[10];
    			
    clock_t timeStart = clock();								
        for(long i=0; i< value; ++i)
        {
        	try {
        		snprintf(buf, 10, "%d", rand());
    			//multimap 不可使用 [] 進行 insertion 
    			c.insert(pair<long,string>(i,buf));
    		}
    		catch(exception& p) {
    			cout << "i=" << i << " " << p.what() << endl;	
    			abort();
    		}
    	}
    	cout << "milli-seconds : " << (clock()-timeStart) << endl;		
    	cout << "unordered_multimap.size()= " << c.size() << endl;	
    	cout << "unordered_multimap.max_size()= " << c.max_size() << endl;	//357913941	
    	
    long target = get_a_target_long();		
        timeStart = clock();		
    auto pItem = c.find(target);								
    	cout << "c.find(), milli-seconds : " << (clock()-timeStart) << endl;		 
    	if (pItem != c.end())
        	cout << "found, value=" << (*pItem).second << endl;
      	else
        	cout << "not found! " << endl;		
    }															 
    }
    
    

    使用set容器

    • 不允许元素重复
    #include <set>
    #include <stdexcept>
    #include <string>
    #include <cstdlib> //abort()
    #include <cstdio>  //snprintf()
    #include <iostream>
    #include <ctime> 
    namespace jj13
    {
    void test_set(long& value)
    {
    	cout << "
    test_set().......... 
    ";
         
    set<string> c;  	
    char buf[10];
    
    clock_t timeStart = clock();								
        for(long i=0; i< value; ++i)
        {
        	try {
        		snprintf(buf, 10, "%d", rand());
            	c.insert(string(buf));     					
    		}
    		catch(exception& p) {
    			cout << "i=" << i << " " << p.what() << endl;	
    			abort();
    		}
    	}
    	cout << "milli-seconds : " << (clock()-timeStart) << endl;		
    	cout << "set.size()= " << c.size() << endl;
    	cout << "set.max_size()= " << c.max_size() << endl;	   //214748364
    		
    string target = get_a_target_string();	
    	{
        timeStart = clock();
    auto pItem = find(c.begin(), c.end(), target);	//比 c.find(...) 慢很多	
    	cout << "std::find(), milli-seconds : " << (clock()-timeStart) << endl;		
    	if (pItem != c.end())
        	cout << "found, " << *pItem << endl;
      	else
        	cout << "not found! " << endl;	
     	}
     	
     	{
        timeStart = clock();		
    auto pItem = c.find(target);		//比 std::find(...) 快很多							
    	cout << "c.find(), milli-seconds : " << (clock()-timeStart) << endl;		 
    	if (pItem != c.end())
        	cout << "found, " << *pItem << endl;
      	else
        	cout << "not found! " << endl;	
     	}							
    }															 
    }
    

    使用map容器

    • 不允许元素键重复
    • c[i]=string(buf)组成pair,允许这样进行插入操作
    #include <map>
    #include <stdexcept>
    #include <string>
    #include <cstdlib> //abort()
    #include <cstdio>  //snprintf()
    #include <iostream>
    #include <ctime> 
    namespace jj14
    {
    void test_map(long& value)
    {
    	cout << "
    test_map().......... 
    ";
         
    map<long, string> c;  	
    char buf[10];
    			
    clock_t timeStart = clock();								
        for(long i=0; i< value; ++i)
        {
        	try {
        		snprintf(buf, 10, "%d", rand());
    			c[i] = string(buf);  					
    		}
    		catch(exception& p) {
    			cout << "i=" << i << " " << p.what() << endl;	
    			abort();
    		}
    	}
    	cout << "milli-seconds : " << (clock()-timeStart) << endl;	
    	cout << "map.size()= " << c.size() << endl;	
    	cout << "map.max_size()= " << c.max_size() << endl;		//178956970
    	
    long target = get_a_target_long();		
        timeStart = clock();		
    auto pItem = c.find(target);								
    	cout << "c.find(), milli-seconds : " << (clock()-timeStart) << endl;		 
    	if (pItem != c.end())
        	cout << "found, value=" << (*pItem).second << endl;
      	else
        	cout << "not found! " << endl;			
        	
        c.clear();					
    }															 
    }
    

    使用unorder_set容器

    #include <unordered_set>
    #include <stdexcept>
    #include <string>
    #include <cstdlib> //abort()
    #include <cstdio>  //snprintf()
    #include <iostream>
    #include <ctime> 
    namespace jj15
    {
    void test_unordered_set(long& value)
    {
    	cout << "
    test_unordered_set().......... 
    ";
         
    unordered_set<string> c;  	
    char buf[10];
    			
    clock_t timeStart = clock();								
        for(long i=0; i< value; ++i)
        {
        	try {
        		snprintf(buf, 10, "%d", rand());
            	c.insert(string(buf));    			 		
    		}
    		catch(exception& p) {
    			cout << "i=" << i << " " << p.what() << endl;	
    			abort();
    		}
    	}
    	cout << "milli-seconds : " << (clock()-timeStart) << endl;		
    	cout << "unordered_set.size()= " << c.size() << endl;	
    	cout << "unordered_set.max_size()= " << c.max_size() << endl;  //357913941
    	cout << "unordered_set.bucket_count()= " << c.bucket_count() << endl;	
    	cout << "unordered_set.load_factor()= " << c.load_factor() << endl;	
    	cout << "unordered_set.max_load_factor()= " << c.max_load_factor() << endl;	
    	cout << "unordered_set.max_bucket_count()= " << c.max_bucket_count() << endl;			
      	for (unsigned i=0; i< 20; ++i) {
        	cout << "bucket #" << i << " has " << c.bucket_size(i) << " elements.
    ";
      	}			
    	
    string target = get_a_target_string();	
    	{
        timeStart = clock();
    auto pItem = find(c.begin(), c.end(), target);	//比 c.find(...) 慢很多	
    	cout << "std::find(), milli-seconds : " << (clock()-timeStart) << endl;		
    	if (pItem != c.end())
        	cout << "found, " << *pItem << endl;
      	else
        	cout << "not found! " << endl;	
     	}
     
     	{
        timeStart = clock();		
    auto pItem = c.find(target);		//比 std::find(...) 快很多							
    	cout << "c.find(), milli-seconds : " << (clock()-timeStart) << endl;		 
    	if (pItem != c.end())
        	cout << "found, " << *pItem << endl;
      	else
        	cout << "not found! " << endl;	
     	}	
    }															 
    }
    

    使用unorder_map容器

    #include <unordered_map>
    #include <stdexcept>
    #include <string>
    #include <cstdlib> //abort()
    #include <cstdio>  //snprintf()
    #include <iostream>
    #include <ctime> 
    namespace jj16
    {
    void test_unordered_map(long& value)
    {
    	cout << "
    test_unordered_map().......... 
    ";
    
    unordered_map<long, string> c;  	
    char buf[10];
    			
    clock_t timeStart = clock();								
        for(long i=0; i< value; ++i)
        {
        	try {
        		snprintf(buf, 10, "%d", rand());
    			c[i] = string(buf);  		
    		}
    		catch(exception& p) {
    			cout << "i=" << i << " " << p.what() << endl;	
    			abort();
    		}
    	}
    	cout << "milli-seconds : " << (clock()-timeStart) << endl;		
    	cout << "unordered_map.size()= " << c.size() << endl;	//357913941
    	cout << "unordered_map.max_size()= " << c.max_size() << endl;	
    	
    long target = get_a_target_long();		
        timeStart = clock();	
    //! auto pItem = find(c.begin(), c.end(), target);	//map 不適用 std::find() 			
    auto pItem = c.find(target);
    						
    	cout << "c.find(), milli-seconds : " << (clock()-timeStart) << endl;		 
    	if (pItem != c.end())
        	cout << "found, value=" << (*pItem).second << endl;
      	else
        	cout << "not found! " << endl;		
    }															 
    }
    

    hash_set/hash_map/hash_multiset/hash_multimap

    • 包含gnu C的编译器就可以

    • 包含的头文件可能需要修改#include<...>非标准容器,由于时间的原因,没有放在一起,在C++11大会之前就出现了!

    • 测试

    /*
    以下測試 hash_multiset, hash_multimap 過程中遇到阻礙:
    headers <hash_set> 和 <hash_map> 各有兩個,
    分別在 ...4.9.2includec++ackward 和 ...4.9.2includec++ext,
    不知要用哪一組! 
    用 <ext...> 那一組會有問題 
       ...4.9.2includec++ackwardhashtable.h 
       [Error] no match for call to '(const hasher {aka const __gnu_cxx::hash<std::basic_string<char> >}) (const key_type&)'
    用 <backward...> 那一組有相同的問題.  
    so, 放棄測試 (no insertion or push_back or ...).  
    */
    
    #include <exthash_set>		
        //...4.9.2includec++ackwardackward_warning.h	
    	//[Warning] #warning This file includes at least one deprecated or antiquated header 
    	//which may be removed without further notice at a future date. 
    	//Please use a non-deprecated interface with equivalent functionality instead. 
    	//For a listing of replacement headers and interfaces, consult the file backward_warning.h. 
    	//To disable this warning use -Wno-deprecated. [-Wcpp]
    	
    #include <stdexcept>
    #include <string>
    #include <cstdlib> //abort()
    #include <cstdio>  //snprintf()
    #include <iostream>
    #include <ctime> 
    namespace jj11
    {
    void test_hash_multiset(long& value)
    {
    	cout << "
    test_hash_multiset().......... 
    ";
       
    	__gnu_cxx::hash_multiset<string> c;  	
    	char buf[10];
    			
        clock_t timeStart = clock();								
        for(long i=0; i< value; ++i)
        {
        	try {
        		snprintf(buf, 10, "%d", rand());
            	//! c.insert(string(buf));     		
    		}
    		catch(exception& p) {
    			cout << "i=" << i << " " << p.what() << endl;	
    			abort();
    		}
    	}
    	cout << "milli-seconds : " << (clock()-timeStart) << endl;				
    }															 
    }
    //---------------------------------------------------
    #include <exthash_map>
        //...4.9.2includec++ackwardackward_warning.h	
    	//[Warning] #warning This file ... (如上個函數所言)
    #include <stdexcept>
    #include <string>
    #include <cstdlib> //abort()
    #include <cstdio>  //snprintf()
    #include <iostream>
    #include <ctime> 
    namespace jj12
    {
    void test_hash_multimap(long& value)
    {
    	cout << "
    test_hash_multimap().......... 
    ";
         
    	__gnu_cxx::hash_multimap<long, string> c;  	
    	char buf[10];
    			
        clock_t timeStart = clock();								
        for(long i=0; i< value; ++i)
        {
        	try {
        		snprintf(buf, 10, "%d", rand());
            	//c.insert(...   		
    		}
    		catch(exception& p) {
    			cout << "i=" << i << " " << p.what() << endl;	
    			abort();
    		}
    	}
    	cout << "milli-seconds : " << (clock()-timeStart) << endl;		
    	
        timeStart = clock();								
        //! auto ite = c.find(...
    	cout << "milli-seconds : " << (clock()-timeStart) << endl;		
    }												
    }
    
  • 相关阅读:
    Java 面向对象(二)封装
    Java 面向对象(一)面向对象思想
    Java 字符串(二)字符串常用操作
    Java 字符串(一)字符串初始化
    JavaScript 流程控制(二)循环结构
    【剑指Offer-知识迁移能力】面试题58:翻转单词顺序
    【剑指Offer-知识迁移能力】面试题57.2:和为s的连续整数序列
    【剑指Offer-知识迁移能力】面试题57:合为s的两个数字
    【剑指Offer-知识迁移能力】面试题56:数组中只出现一次的两个数字
    【剑指Offer-知识迁移能力】面试题55.2:平衡二叉树
  • 原文地址:https://www.cnblogs.com/ranjiewen/p/6942598.html
Copyright © 2011-2022 走看看