算法學習筆記(一)C++排序函數、映射技巧與字典樹


1.頭文件algorithm中有函數sort()用於排序,參數為:排序起始地址,排序結束地址,排序規則(返回bool型)
例如,要將array[] = {5,7,1,2,9}升序排列,則使用:

bool cmp(int a,int b);int main()
{
    int array[] = {5,7,1,2,9};
    sort(array,array+5,cmp);
    for(int i = 0;i < 5;i++)
        cout << array[i] << " ";
    cout << endl;
    return 0;
}

bool cmp(int a,int b)
{
    if(a>b) return false;
    else return true;
}

注:1.在C語言中,使用qsort進行排序。

    2.如果不指定排序方式,默認為升序。



2.對於有序映射關系,可以用巧妙的辦法轉化,例如:

ABC對應2,DEF對應3,GHI對應4,JKL對應5,MNO對應6,PRS對應7,TUV對應8,WXY對應9

要把一串字符按照這樣的規則映射為數字,可以采用以下方法:

(*(p+i) - 'A' - (*(p+i)>'Q'))/3 + 2

其中p為指向字符串的指針,因為每3個字母變化一次映射關系,因此只需要判斷當前字符距離字符A的距離,然后除以三判斷落在哪一組。需要注意的是字母Q不包含在映射關系當中,因此當字符在Q之后時,應該減去1個字符的距離再進行判斷。


3.字典樹是一種存放字符串的樹形結構,又稱為單詞查找樹,利用的是字符串的公共前綴來減少查詢時間。需要注意的是字典樹常常用於統計單詞出現次數,而不是為了取出單詞去存儲單詞。一般字典樹的結構體如下:

struct DirectionTree{    int count;//計數到當前節點為止的單詞個數    bool terminal;//記錄此節點無子節點    DirectionTree* child[26];//該節點的子節點}*root;//字典樹的根節點,根節點不包含任何字母

字典樹的存放方式為根連接子節點,子節點連接新的節點,一直連接到尾部。例如存儲字符"abc","ad",則數據結構如下:

wKiom1QeTZfwrCSjAAEA2r9xqMQ124.jpg

其中只有D3和D4兩個節點的terminal值為true,count為1,其余的均為false,0。當再次添加同樣的字符串時,不會創建新的節點,只會引起count加1。

完整代碼如下(轉):

#include <string>#include <cstring>#include <cstdlib>#include <cstdio>#include <algorithm>#include <iostream>#include <assert.h>using namespace std;#define MAX 26    //the total number of alphabet is 26, a...zstruct Dictree{    bool word;    int count;    struct Dictree *trie[MAX];    // the 26 child} * a;int init()        // init the chained list{    a = new Dictree;    for(int i = 0; i < MAX; i++)    {        a->trie[i] = NULL;        a->word = false;    }    return 0;}bool searchTrie(char *str){    int len, res;    Dictree *head = a;    assert(head);    len = strlen(str);    for(int i = 0; i < len; i++)    {        res = (int)(str[i] - 'a');        if(head->trie[res] == NULL)            return false;        head = head->trie[res];    }    if(head->word)        return true;    return false;}int insertTrie(char *str){    int len, res;    Dictree *head = a;    len = strlen(str);    for(int i = 0; i < len; i++)    {        res = int(str[i] - 'a');        if(head->trie[res] == NULL)        //whether the node exist?        {            head->trie[res] = new Dictree;            head = head->trie[res];            head->count = 0;            for(int j = 0; j < MAX; j++)            {                head->trie[j] = NULL;                head->word = false;            }        }        else            head = head->trie[res];    }    head->count++;    head->word = true;    return head->count;}int main(){    char str[20];    init();    for(int i = 0; i < 10; i++)    {        scanf("%s", str);        printf("%d\n", insertTrie(str));    }    scanf("%s", str);    printf("%s\n", searchTrie(str) ? ("YES"):("NO"));    return 0;}



注意!

本站转载的文章为个人学习借鉴使用,本站对版权不负任何法律责任。如果侵犯了您的隐私权益,请联系我们删除。



 
粤ICP备14056181号  © 2014-2021 ITdaan.com