leetcode -- Largest Number

原題:

Given a list of non negative integers, arrange them such that they form the largest number.

For example, given [3, 30, 34, 5, 9], the largest formed number is 9534330.

Note: The result may be very large, so you need to return a string instead of an integer.

該題最好的解法就是對序列進行排序,關鍵在於排序的比較函數。比較的準則是:看比較函數的兩個參數按一前一後兩種法案,拼接成字符串後,那種方案得到的字符串字典序大。

這裏,借用這題來比較C中的qsort函數和STL中sort函數的區別。

解法一:使用C中的qsort函數。

string IntToStr(int n) {
	string res;

	if(n == 0) {
		res += '0';
		return res;
	}

	while(n) {
		res += n % 10 + '0';
		n /= 10; 
	}

	reverse(res.begin(), res.end());
	return res;
}
int CMP(const void *iter1, const void *iter2) {
	string s1, s2;
	int * it1 = (int *)iter1;
	int * it2 = (int *)iter2;


	s1 = IntToStr(*it1);
	s2 = IntToStr(*it2);

	if(s1 + s2 < s2 + s1)
		return 1;
	else if(s1 + s2 > s2 + s1)
		return -1;
	else
		return 0;
}	

class Solution {
public:
    string largestNumber(vector<int> &num) {
		int* a = new int[num.size()];
		for(int i = 0; i != num.size(); i++)
			a[i] = num[i];

		//vector<int>::iterator it1 = num.begin();
		//vector<int>::iterator it2 = num.end();

		int (*cmpfunp)(const void *, const void *);
		cmpfunp = CMP;

        qsort(a, num.size(), sizeof(int), cmpfunp);

		string res;

		for(int i = 0; i != num.size(); i++) {
			res += IntToStr(a[i]);
		}
		
		int flag = 0;
		for(int i = 0; i != res.size(); i++) {
			if(res[i] != '0'){
				flag = 1;
				break;
			}
		}
		if(flag == 0) {
			res = "0";
		}

		return res;
	}

};
需要注意的是,void qsort(void *base,int nelem,int width,int (*fcmp)(const void *,const void *));

四個參數分別是:

1 待排序數組首地址
2 數組中待排序元素數量
3 各元素的佔用空間大小
4 指向函數的指針,用於確定排序的順序
函數指針的形式必須是int (*fcmp)(const void *, const void *), const不能少,void也不能換成其他類型,只能在比較函數的內部根據實際比較的元素類型進行強制類型轉換。因爲qsort是C中的函數,其內部機制是直接操作void類型的指針,因此不能對C++中的容器進行直接排序,此題規定輸入時vector<int>,所以如果非要使用qsort,只能用int數組暫存vector<int>。

使用qsort對其他類型進行排序時也有一些需要注意的地方,詳見博客:http://www.cnblogs.com/syxchina/archive/2010/07/29/2197382.html

解法二:使用STL中的sort函數。

string IntToStr(int n) {
	string res;

	if(n == 0) {
		res += '0';
		return res;
	}

	while(n) {
		res += n % 10 + '0';
		n /= 10; 
	}

	reverse(res.begin(), res.end());
	return res;
}
	
bool STL_CMP(int &a, int &b) {
	string s1, s2;

	s1 = IntToStr(a);
	s2 = IntToStr(b);

	if(s1 + s2 > s2 + s1)
		return true;
	else 
		return false;
}
class Solution {
public:
    string largestNumber(vector<int> &num) {

		sort(num.begin(), num.end(), STL_CMP);

		string res;

		for(int i = 0; i != num.size(); i++) {
			res += IntToStr(num[i]);
		}
		
		int flag = 0;
		for(int i = 0; i != res.size(); i++) {
			if(res[i] != '0'){
				flag = 1;
				break;
			}
		}
		if(flag == 0) {
			res = "0";
		}

		return res;
	}

};
STL中的sort函數有多個重載的版本,第三個參數(比較函數)可以省去,如果省去,則默認是產生一個按operate<排列的序列。

sort的第三個參數可以函數指針(如以上代碼),也可以是仿函數。如果是函數指針,則形式應該是bool (*cmp)(TYPE &a, TYPE &b),返回值是bool,而qsort的返回值是int。

這裏的sort和qsort一樣是非穩定排序,STL中的排序算法還有其他變種,如stable_sort等。

關於STL中的sort詳見博客:

http://blog.163.com/lovelychicken0824@126/blog/static/2277337420071894051206/

http://www.cppblog.com/mzty/archive/2005/12/15/1770.html

發佈了48 篇原創文章 · 獲贊 26 · 訪問量 18萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章