美文网首页C语言
(改进版)宏实现C语言任意类型的安全数组

(改进版)宏实现C语言任意类型的安全数组

作者: 黑熊小李 | 来源:发表于2022-10-31 11:30 被阅读0次

    前述

    在我的上一篇文章《利用宏实现C语言任意类型的安全数组》中留下的代码,经过我反复品味,发现还有一些不足,例如:

    1. Create_Array 宏的模块化程度不高,有比较重的散装感,也就是耦合度高。
    2. Destroy_Array 宏没有对于情况的仔细分析处理分支,不安全。
    3. 原Array 结构体不应该别称为Array ,它更像是一种通用的安全结构。
    4. 命名上的不规范,不能达到显而易见的效果。

    改进

    针对以上不足,做出如下改进:

    1. 规范了命名,使得通过名字就能确定所属关系和类型。
    2. 抽象出一个通用的 Box 结构,避免歧义。
    3. 使用单个函数封装了创建 Box 结构的功能,模块化成度更高。
    4. 简化宏的结构,为宏添加必要的处理分支。
    5. 添加了必要的注释,方便阅读。

    代码:

    #include<stdio.h>
    #include<stdlib.h>
    
    // 可以通用的 内容+大小 结构
    typedef struct {
        size_t size;
        void *private; 
    }Box;
    
    // 创建一个Box对象,并为私有成员开辟需要的空间
    Box *Box_new(size_t size, size_t typesize) {
        Box *out = calloc(1, sizeof(Box));
        
        if (out != NULL) {
            out->private = calloc(size,typesize);
            
            if (out->private != NULL) { 
                out->size = size; 
                return out;
            }
            else { 
                free(out);
                out=NULL; 
            }
        }
    
        return out;
    }
    
    // 释放分配的空间
    void Box_delete(Box *opj){
        if(opj->private != NULL) {
            free(opj->private);
        }
        
        free(opj); 
    }
    
    /** if 分配成功 
     *      生成两个指针
     *          一个指向结构
     *          一个具象化的类型指针,指向结构中的私有成员 
     * else 两个堆内存,任意一个分配失败
     *      生成两个空指针
    */
    #define Box_get_as_type(name, type)                    \
        type *name##_ptr = NULL;                           \
        if(name != NULL) { name##_ptr = name->private; }   \
    
    
    #define Box_create(name, type, length)                 \
        Box *name = Box_new(length, sizeof(type));         \
    
    /** if 数组指针不为空
     *  分配的内存,遵循由内部向外部逐步释放原则
     *      优先把 private 的别名指针置空
     *      清理结构体内部动态内存
     *      清理结构体动态内存
    */
    #define Box_destory(name)         \
        if(name) {                    \
            Box_delete(name);         \
            name=NULL;                \
        }
    
    void fn(int *opj, size_t size){
        for(int i=0; i < size; i++) {
            opj[i]=i*2;
            if(i < size-1) printf("%d->",opj[i]);
            else printf("%d\n总数:%zu 个\n",opj[i],size);
        }
    }
    
    int main(){  
        Box_create(an, int, 10)
        Box_get_as_type(an, int)
        if(an) fn(an_ptr, an->size);
        Box_destory(an)
    } 
    

    结果:

    Safe_Power

    疑问:

    在之前印象里,free函数只是释放了这个指针指向的地址,指针值应该不变,但是在这里,结构体中 private 指针释放后,值发生变化,而结构体指针的值却不变的?!都是calloc分配的,怎么会有诡异的现象?虽然不耽误啥,但就是想不通。


    注意

    文章为本人在简书平台原创,盗用必究!

    相关文章

      网友评论

        本文标题:(改进版)宏实现C语言任意类型的安全数组

        本文链接:https://www.haomeiwen.com/subject/wvyrtdtx.html