zoukankan      html  css  js  c++  java
  • 用 void* 编写泛型函数

    1.泛型交换

    //1.编写int类型的swap
    void swap(int *vp1, int *vp2) {
        int a = *vp1;
        *vp1 = *vp2;
        *vp2 = a;
    }
    //2.引申至泛型swap
    void swap(void *vp1, void *vp2, int size){
        char buffer[size];
        memcpy(buffer, vp1, size);
        memcpy(vp1, vp2, size);
        memcpy(vp2, buffer, size);
    }

    使用泛型swap交换C-string:

    char* husband = "Fred";
    char* wife = "Wilma";
    swap(&husband,&wife,sizeof(char));

    2.泛型线性搜索

    //1.编写int类型的lsearch
    int * lsearch(int key ,int* array, int size){
        for (int i = 0; i < size; i++)  
        {
            if(array[i] == key)
                return i;
        }
        return NULL;
    }
    //2.编写泛型lsearch
    int *lsearch(void *key, void *base, int size, int elementSize){
        for (int i = 0; i < size; i++) {
          void * elemAddr = (char *)base + i * elemSize; 
          if (memcmp(key, elemAddr, elemSize) == 0)
            return elemAddr;
        }       
        return NULL;
    }

    如果用泛型lsearch来搜索C-string,因为C-string的长度不是固定的,故无法利用memcmp进行比较。可以利用函数指针实现:

    int *lsearch(void *key, void *base, int size, int elementSize,int (*cmpFunc)(void *,void *)){
        for (int i = 0; i < size; i++) {
          void * elemAddr = (char *)base + i * elemSize; 
          if (cmpFunc(key, elemAddr) == 0)
            return elemAddr;
        }       
        return NULL;
    }

    实现cmpFunc:

    //比较int
    int intCmp(void *elem1,void *elem2){
        int *ip1 = elem1;
        int *ip2 = elelm2;
        return *ip1-*ip2;
    }
    //比较C-string
    int strCmp(void *elem1,void *elem2){
        char *s1 = *(char**)elem1;
        char *s2 = *(char**)elem2;
        return strcmp(s1,s2);
    }

    3.泛型二分搜索

    void *binary_search(void *key,void *base,int n,int elemSize,int (*cmpFunc)(void *,void *)){
        int low = 0;
        int high = n-1;
        while(low <= high){    
            int mid = low+(high-low)/2;
            void *midAddr = (char*)base+mid*elemSize;
            if(cmpFunc(key,midAddr) == 0){
                return midAddr;
            }
            else if(cmpFunc(key,midAddr) < 0){
                high = mid-1;
            }
            else{
                low = mid+1;
            }
        }
        return NULL;
    }

    编码验证:

    #include<iostream>
    using namespace std;
    
    int intCmp(void *elem1,void *elem2){
        int *ip1 = (int*)elem1;
        int *ip2 = (int*)elem2;
        return *ip1-*ip2;
    }
    
    void *binary_search(void *key,void *base,int n,int elemSize,int (*cmpFunc)(void *,void *)){
        int low = 0;
        int high = n-1;
        while(low <= high){
            int mid = low+(high-low)/2;
            void *midAddr = (char*)base+mid*elemSize;
            if(cmpFunc(key,midAddr) == 0){
                return midAddr;
            }
            else if(cmpFunc(key,midAddr) < 0){
                high = mid-1;
            }
            else{
                low = mid+1;
            }
        }
        return NULL;
    }
    
    int main(){
        int a[]={1,2,3,4,5,6,7,8,9};
        int i;
        for(i=1;i<10;i++){
        
            cout<<((int*)binary_search(&i,a,9,sizeof(int),intCmp))<<endl;        
        }    
        return 0; 
    } 
    View Code

    运行截图:

  • 相关阅读:
    Zabbix5 Frame 嵌套
    Zabbix5 对接 SAML 协议 SSO
    CentOS7 安装 Nexus
    CentOS7 安装 SonarQube
    GitLab 后台修改用户密码
    GitLab 查看版本号
    GitLab Admin Area 500 Error
    Linux 安装 PostgreSQL
    Liger ui grid 参数
    vue.js 是一个怪东西
  • 原文地址:https://www.cnblogs.com/bukekangli/p/4319486.html
Copyright © 2011-2022 走看看