• 散列表(1)-集合/用位向量实现集合


     目录

    1_集合

    1.1_集合的定义

    1.2_集合的记号

    1.3_定义在集合上的基本运算

    2_用位向量实现集合(附实现代码☟)


    在这里插入图片描述

    1_集合

    1.1_集合的定义

    集合是表示事物的最有效的数学工具之一。

    集合是由元素(成员)组成的一个类。集合的成员可以是一个集合,也可以是一个原子。
    同一个元素在一个集合中不能多次出现。
    有时需要表示有重复元素的集合,这时允许同一个元素在集合中多次出现。这样的集合称为多重集合

    1.2_集合的记号

    当集合中的原子具有线性序关系(或称全序关系)“<”时,称集合为有序集(全序集或线性序集)。“<”是集合的一个线性序,它有如下性质:

    1. 若a,b是集合中任意两个原子,则a
    2. 若a,b和c是集合中的原子,且a
    • 将集合的元素称为记录,每个记录有多个项(或域)来表示元素的各种属性。
    • 通过键值可以唯一地确定集合中的一个元素。
    • 键只是元素记录中许多域中的一个。
    • 集合中元素的列举顺序是任意的,如{1,3}和{3,1}表示同一个集合。
    • 关于集合的最基本的运算是并、交、差运算。
    • 设A和B是两个集合。
    • 把他们所有的元素合并在一起组成的集合,叫做集合A与集合B的并集,记作A∪B,读作A并B。
    • 由所有属于集合A且属于集合B的元素所组成的集合,叫做集合A与集合B的交集,记作A∩B
    • 则所有属于A且不属于B的元素构成的集合,叫做集合A减集合B(或集合A与集合B之差),类似地,对于集合A、B,把集合{x∣x∈A,且x∉B}叫做A与B的差集。例如:
    • A={1,2,3},B={2,4},则A-B={1,3}。

    1.3_定义在集合上的基本运算

    约定:其中大写字母表示一个集合,小写字母表示集合中的一个元素

    • Set_Union(A, B):并集运算
    • Set_Intersection(A, B):交集运算
    • Set_Difference(A, B):差集运算
    • Set_Assign(A, B):赋值运算(将B的元素赋给A)
    • Set_Equal(A, B):判等运算
    • Set_Member(A, B):成员运算
    • Set_Insert(x, S):插入运算
    • Set_Delete(x, S):删除运算

    2_用位向量实现集合

    • 位向量是一种每个元素都是二进制位(即0/1值)的数组

    位向量实现的集合结构Bitset定义

    1. typedef struct bitset *Set; /* 位向量集合指针类型 */
    2. typedef struct bitset {
    3. int setSize; /* 集合大小 */
    4. int arraySize; /* 位数组大小 */
    5. unsigned short* v; /* 位数组 */
    6. }Bitset;

    创建一个用位向量实现、可存储集合大小为size的空集

    1. Set SetInit(int size)
    2. {
    3. Set S = (Set)malloc(sizeof * S);
    4. S->setSize = size;
    5. /* 存储大小为setsize的集合所需的无符号短整数位数 */
    6. S->arraySize = (size + 15) >> 4;
    7. S->v = (unsigned short*)malloc(size * sizeof(unsigned short));
    8. /* 初始化为空集 */
    9. for (int i = 0; i < size; i++) S->v[i] = 0;
    10. return S;
    11. }

    通过复制表示集合的位向量来实现赋值运算

    1. void SetAssign(Set A, Set B)
    2. {
    3. /* 集合赋值运算 */
    4. if (A->arraySize != B->arraySize) return;
    5. for (int i = 0; i < A->arraySize; i++) A->v[i] = B->v[i];
    6. }

    通过检测元素在表示集合的位向量中相应的位来判断成员的属性

    1. int SetMember(int x, Set S)
    2. {
    3. /* 成员属性判断 */
    4. if (x < 0 || x > S->setSize) return 0;
    5. return S->v[ArrayIndex(x)] & BitMask(x);
    6. }

    下标定位函数

    1. int ArrayIndex(int x)
    2. {
    3. /* 右移4位获得x在数组中的位置*/
    4. return x >> 4;
    5. }
    1. /* 位屏蔽函数*/
    2. unsigned short BitMask(int x)
    3. {
    4. /* 确定x在相应数组单元中的准确位置 */
    5. return 1 << (x & 15);
    6. }
    7. /* 判断集合相等函数 */
    8. int SetEqual(Set A, Set B)
    9. {
    10. /* 判断集合A和集合B是否相等*/
    11. if (A->arraySize != B->arraySize) return 0;
    12. int retval = 1;
    13. for(int i = 0; i < A->arraySize; i ++ )
    14. if (A->v[i] != B->v[i]) {
    15. retval = 0;
    16. break;
    17. }
    18. return retval;
    19. }
    20. /* 并集运算 */
    21. Set SetUnion(Set A, Set B)
    22. {
    23. Set tmp = SetInit(A->setSize);
    24. for (int i = 0; i < A->arraySize; i++)
    25. tmp->v[i] = A->v[i] | B->v[i];
    26. return tmp;
    27. }
    28. /* 交集运算 */
    29. Set SetIntersection(Set A, Set B)
    30. {
    31. Set tmp = SetInit(A->setSize);
    32. for (int i = 0; i < A->arraySize; i++)
    33. tmp->v[i] = A->v[i] & B->v[i];
    34. return tmp;
    35. }
    36. /* 差集运算 */
    37. Set SetDifference(Set A, Set B)
    38. {
    39. Set tmp = SetInit(A->setSize);
    40. for (int i = 0; i < A->arraySize; i++)
    41. tmp->v[i] = A->v[i] ^ B->v[i];
    42. return tmp;
    43. }
    44. /* 元素插入运算 */
    45. void SetInsert(int x, Set S)
    46. {
    47. if (x < 0 || x >= S->setSize) return;
    48. S->v[ArrayIndex(x)] |= ~BitMask(x);
    49. }
    50. /* 元素删除运算 */
    51. void SetInsert(int x, Set S)
    52. {
    53. if (x < 0 || x >= S->setSize) return;
    54. S->v[ArrayIndex(x)] &= ~BitMask(x);
    55. }
  • 相关阅读:
    springboot上线打包+vuecli2部署在linux服务器上(打包上线)
    指针——C语言初阶
    Qt不能安装自己想要的版本,如Qt 5.15.2
    中尺度混凝土二维有限元求解——运行弯曲、运行光盘、运行比较、运行半圆形(Matlab代码实现)
    竞赛 基于大数据的社交平台数据爬虫舆情分析可视化系统
    RT-Thread STM32F407 五步完成OLED移植
    css3新特性有哪些?
    【Oracle】 instr函数与substr函数以及自制分割函数
    C++编程功底和常用规则
    从入门开始手把手搭建千万级Java算法测试-主页面的搭建和自定义测试数组生成类
  • 原文地址:https://blog.csdn.net/forever_bryant/article/details/127584764