文章目录

  • 初始化
  • 加密
  • 解密
  • 密文slot之间移位
  • 密文乘明文矩阵
  • 密文乘密文

代码来自HElib中CKKS的示例 HElib/examples/tutorial,将所有示例代码做了总结并加了一些注解。

初始化

//头文件、命名空间
#include <helib/helib.h>using namespace std;
using namespace helib;Context context =ContextBuilder<CKKS>().m(32 * 1024).bits(358).precision(20).c(6).build();
//使用builder初始化一个Context对象,具体参数在后面详细说明cout << "securityLevel=" << context.securityLevel() << "\n";
//打印出估计的安全等级long n = context.getNSlots();
//获取slot的个数,n=m/4
//在CKKS方案中,明文是实数(复数)的向量,向量的长度为n,n的大小有参数决定。向量的每个组成称为slot,下标为{0,1,2,n-1},n即为slot的个数SecKey secretKey(context);secretKey.GenSecKey();
//创建一个私钥对象,要和指定的context联系在一起const PubKey& publicKey = secretKey;
//在HElib中,私钥类是公钥类的子类,可以用上述方法创建一个公钥对象
  1. m 是"cyclotomic index",m必须是 2 的指数,当m增加,安全性增加,slot增多,但是执行速度变慢,密文大小增大
  2. bits 指定"ciphertext modulus"的比特位数,bits 增大,安全性降低,但可以执行更深层的同态计算,密文大小增大
  3. precision 指定了数据在编码、加密或解密时精度的位数,precision 增大,允许的同态计算的深度减小,但是安全性和运行效率不受影响,另外 precision 最好不要大于 40
  4. c 指定了key-switching matrices 的列数。c 增大,安全性会有一点增大,但是运行速度下降,公钥占用的内存增大。c至少为 2但最好不超过 8。

建议参数的设置要服从以下配置,可满足至少128位的安全性

m bits c
16384 119 2
32768 358 6
32768 299 3
32768 239 2
65536 725 8
65536 717 6
65536 669 4
65536 613 3
65536 558 2
131072 1445 8
131072 1435 6
131072 1387 5
131072 1329 4
131072 1255 3
131072 1098 2
262144 2940 8
262144 2870 6
262144 2763 5
262144 2646 4
262144 2511 3
262144 2234 2

加密

//第一种加密方式vector<double> v(n);for (long i = 0; i < n; i++)v[i] = sin(2.0 * PI * i / n);
//声明一个长度为n的vector,赋予任意值。PI由HElib定义PtxtArray p(context, v);
//将明文vector装进一个特殊类型的容器PtxtArray。PtxtArray要和Context对象关联
//很多类型的vector都可以装进PtxtArray对象(int, long, double, complex<double>)
//上述过程也可分两步:PtxtArray p(context); p.load(v);
//其实这里做了encoding的工作Ctxt c(publicKey);
//创建密文,要和公钥关联p.encrypt(c);
//加密p存入c
//由于密文总是关联一个公钥,所以加密的时候不用传公钥cout << "c.capacity=" << c.capacity() << " ";cout << "c.errorBound=" << c.errorBound() << "\n";
//输出密文的capacity和absolute error

depth
在CKKS方案中,密文存在一定的“noise”,同态计算的层次加深,noise增大,会降低密文的capacityaccuracy

  1. 密文的capacity一开始略小于创建Context对象时设定的bits参数,每次同态计算后,都会再下降,当capacity小于1,密文就不能被解密了。
  2. 密文的accuracy计算的是ciphertext c 对比于应该加密的plaintext p 的absolute error,该值不能大于2^{-precision},precision是创建Context对象时设定的,每次同态计算后,absolute error都会增大

//第二种加密方式PtxtArray p(context);
//创建一个PtxtArray对象关联Context对象p.random();
//用随机数填充n个slots,interval [0,1]Ctxt c(publicKey);p.encrypt(c);
//加密p存入c//===================================================//加密一群随机密文int len = 3;vector<PtxtArray> p, q;
//创建元素为PtxtArray对象的vectorfor (int i = 0; i < len; i++) {p.emplace_back(context);p[i].random();q.emplace_back(context);q[i].random();}
//每个PtxtArray对象都要和Context对象关联// p[i] is a random PtxtArray for i = 0..len-1// q[i] is a random PtxtArray for i = 0..len-1vector<Ctxt> c, d;for (int i = 0; i < len; i++) {c.emplace_back(publicKey);p[i].encrypt(c[i]);d.emplace_back(publicKey);q[i].encrypt(d[i]);}// c[i] encrypts p[i] for i = 0..len-1// d[i] encrypts q[i] for i = 0..len-1

解密

  PtxtArray pp(context);
//创建一个PtxtArray对象pp.decrypt(c, secretKey);
//私钥解密c存入ppvector<double> v;pp.store(v);
//pp存入标准的vector类型,可以没有这个操作double distance = Distance(p, pp);cout << "distance=" << distance << "\n";
//计算原始明文和解密后的明文之间的距离// For debugging, you can also make "approximate" comparisons as follows:if (pp == Approx(p))cout << "GOOD\n";elsecout << "BAD\n";// Here, p is the "correct value" and you want to test if pp is "close" to it.// NOTES: The Approx function (which is really a class constructor) takes two// optional arguments://   double tolerance; // default is 0.01//   double floor;     // default is 1.0//// The expression//   a == Approx(b, tolerance, floor)// is true iff Distance(a,b) <= tolerance*max(Norm(b),floor), The idea is// that it checks if the relative error is at most tolerance, unless Norm(b)// itself is too small (as determined by floor). Here, Norm(b) is the max// absolute value of the slots, and Distance(a,b) = Norm(a-b).//// In addition to PtxtArray's, you can compare values of type double or// complex<double>, and vectors of type double or complex<double>.

密文slot之间移位

  Context context =ContextBuilder<CKKS>().m(32 * 1024).bits(358).precision(30).c(6).build();cout << "securityLevel=" << context.securityLevel() << "\n";long n = context.getNSlots();SecKey secretKey(context);secretKey.GenSecKey();
//以上是正常的初始化步骤addSome1DMatrices(secretKey);
//为了进行移位操作,需要加上这个
//密钥类是公钥类的子类,addSome1DMatrices的调用需要数据存在密钥中,但是计算出的信息存在公钥中// Recall that SecKey is a subclass of PubKey. The call to addSome1DMatrices// needs data stored in the secret key, but the information it computes is// stored in the public key.const PubKey& publicKey = secretKey;
//创建公钥对象//循环移位rotate(c, 2);// rotate c right by 2:// (c[0], ..., c[n-1]) = (c[n-2], c[n-1], c[0], c[1], ..., c[n-3])rotate(c, -1);// rotate c left by 1// (c[0], ..., c[n-1]) = (c[1], c[2], ..., c[n-1], c[0])//移位,缺位补0shift(c, 2);// rotate c right by 2:// (c[0], ..., c[n-1]) = (0, 0, c[0], c[1], ..., c[n-3])shift(c, -1);// rotate c left by 1// (c[0], ..., c[n-1]) = (c[1], c[2], ..., c[n-1], 0)//所有slot求和的结果放入每个slot// We can also sum all of slots, leaving the sum in each slottotalSums(c);// (c[0], ..., c[n-1]) = (S, ..., S), where S = sum_{i=0}^{n-1} c[i]

密文乘明文矩阵

//需要加入头文件
#include <helib/matmul.h>···正常初始化···MatMul_CKKS mat(context,[n](long i, long j) { return ((i + j) % n) / double(n); });
//定义一个n×n的明文矩阵
//第二个参数代表传两个long型返回double型
//输入(i, j),返回matrix in row i and column j的值Ctxt c0 = c;c0 *= mat;
//密文乘矩阵,c的slot看做行向量//如果给定的矩阵要使用多次,可以做pre-computation来提高运行效率EncodedMatMul_CKKS emat(mat);
//一次pre-computation通过"encoding"矩阵来执行Ctxt c1 = c;c1 *= emat;emat.upgrade();
//做更多的pre-computation来提高运行效率

密文乘密文

//计算 e = sum_{i=0}^{len-1} c[i]*d[i] for (int i = 0; i < len; i++) {Ctxt tmp = c[i];tmp.multLowLvl(d[i]);// tmp is now c[i]*d[i] but in a non-canonical statee += tmp;// e is now c[0]*d[0] + ... c[i]*d[i] but in a non-canonical state}e.reLinearize();
//将e转化为canonical state。
//在本例中这不是必须的,如果e还要用于其他操作,转化为canonical state会使计算效率更高

在CKKS方案中,密文相乘实际上有两步:ctxt1.multLowLvl(ctxt2);ctxt1.reLinearize();第一步会使ctxt1是non-canonical state,经过第二步转换为canonical state
但是在某些操作例如密文加法,能够在non-canonical state直接相加,得到的结果仍为non-canonical state

HElib-源码示例CKKS操作相关推荐

  1. WinForm立体饼状图实现(附源码示例) 之配餐系统的开发

    本文所要将的是在"配餐系统"开发中 立体饼状图效果的实现,直接贴出代码和附上示例,相信需要的朋友可以很容易使用!项目中的效果图,如下: 实现 应用的是 System.Drawing ...

  2. php并发取源码,PHP读取大文件源码示例-Swoole多进程读取大文件

    PHP读取大文件源码示例,通过PHP读取过大.超大型文件的思路及解决方案. 在日常读取文件时,若文件 不是很大,通常使用file_get_contents,将内容一次性载入的变量中,也可以远程加载网页 ...

  3. Linux Zero-copy零拷贝技术:源码示例

    <Linux Zero-copy零拷贝技术:源码示例> <Linux Zero-copy零拷贝技术全面揭秘> <什么是mmap?零拷贝?DMA?> <Linu ...

  4. 视觉机器学习20讲-MATLAB源码示例(19)-遗传算法

    视觉机器学习20讲-MATLAB源码示例(19)-遗传算法 1. 遗传算法 2. Matlab仿真 3. 仿真结果 4. 小结 1. 遗传算法 遗传算法(Genetic Algorithm,GA)最早 ...

  5. html+手机自适应源码,手机端页面自适应解决方案—rem布局(进阶版,附源码示例)...

    一年前笔者写了一篇 <手机端页面自适应解决方案-rem布局>,意外受到很多朋友的关注和喜欢.但随着时间的推移,该方案已然过时,故为大家介绍一个目前我极力推荐使用的,更加完美的方案--rem ...

  6. AR实境壁画源码示例教程大公开

    Kivicube小程序AR原生图像追踪正式免费开放测试了!特别推出AR实境壁画模版案例供大家使用! AR技术能够在现实的基础上构建出无限的虚拟世界,让艺术家们的画布在现实中也能得到无限延伸,为艺术作品 ...

  7. hmac-sha1加密算法C源码示例

    HMAC: Hash-based Message Authentication Code,即基于Hash的消息鉴别码 在各大开放平台大行其道的互联网开发潮流中,调用各平台的API接口过程中,无一例外都 ...

  8. 深入解析Angular Component的源码示例

    本篇文章主要介绍了剖析Angular Component的源码示例,写的十分的全面细致,具有一定的参考价值,对此有需要的朋友可以参考学习下.如有不足之处,欢迎批评指正. Web Component 定 ...

  9. 【Flutter】Flutter 拍照示例 ( Flutter 插件配置 | Flutter 插件源码示例 | iOS 应用配置 | Android 应用配置 )

    文章目录 一.Flutter 插件配置 二.Flutter 插件源码示例 三.iOS 应用配置 四.Android 应用配置 五.相关资源 一.Flutter 插件配置 Flutter 拍照示例中 , ...

最新文章

  1. 为什么会需要HTTPS?
  2. SCIP习题 1.21(寻找最小因子)
  3. webpack优化相关操作
  4. mybaitplus 根据id批量进行修改_批量重命名工具
  5. Android官方导航栏ActionBar(二)—— Action View、Action Provider、Navigation Tabs的详细用法...
  6. WPF 菜单栏滚动到顶部后固定的两种方法
  7. JavaFX技巧20:有很多需要展示的地方吗? 使用画布!
  8. python中enumerate()的理解
  9. Mybatis理解与入门步骤
  10. 漫步数理统计三十二——中心极限定理
  11. 图表中如何实现动态变更分类轴与系列值
  12. Python学习入门基础教程(learning Python)--5.6 Python读文件操作高级
  13. 小D课堂-SpringBoot 2.x微信支付在线教育网站项目实战_2-4.后端项目分层分包及资源文件处理...
  14. 联想微型计算机a20,联想乐player A20
  15. 如何清除本地计算机搜索记录,怎么深度清理电脑使用痕迹?
  16. 建站百科|全网最全、最系统的域名申请教程,不看吃亏!!!
  17. IE和火狐的在js和css上的差别
  18. MacOS 软件版本更新Monterey12.1版之后L2TP无法正常访问内网服务解决方案
  19. Project Euler Problem 66
  20. 初级软件测试面试前需要做什么准备?面试题可以去哪里找?

热门文章

  1. 使用Python+opencv+k-means根据扫描图片计算叶片面积-续
  2. 【51nod P2500】后面第一个大于【单调栈】
  3. 掌门持续交付流水线大规模实践
  4. [附源码]SSM计算机毕业设计渔具店管理系统JAVA
  5. 数字金字塔【两种方法】
  6. 09 MySQL用户管理
  7. leetcode字符串专题
  8. CSS:条纹背景的实现
  9. 工控液晶屏的RGB接口介绍
  10. 过氧化氢低温等离子体灭菌测试