传统加密技术(恺撒+仿射)

本文介绍了两种古典密码学技术——CaesarCipher(恺撒密码)和AffineCipher(仿射密码)。CaesarCipher是一种简单的替换加密,通过字母表上的固定偏移量实现加密和解密。而AffineCipher则基于线性代数,使用一个数学方程对字母进行加密,解密时需要计算乘法逆元。文章提到了在实现AffineCipher解密时需要注意负数的情况。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

1.Caesar cipher恺撒密码

是一种最简单且最广为人知的加密技术。它是一种替换加密的技术,明文中的所有字母都在字母表上向后(或向前)按照一个固定数目进行偏移后被替换成密文。

加密对象:英文字母

密钥格式:k,0<k<26

Caesar加密变换: c = (m + k) mod 26

//加密函数
void Caesar_encrypt(int k, char* m, unsigned int mLen, char* c)
{
	unsigned int i = 0;
	for (i = 0; i < mLen; i++)
	{
		if (m[i] >= 'a' && m[i] <= 'z' - k)
		{
			c[i] = (m[i] - 'a') + ('A' + k);
		}
		else if (m[i] >= 'a' && m[i] > 'z' - k)
		{
			c[i] = (m[i] - 'z' - 1) + ('A' + k);
		}
		else if (m[i] >= 'A' + k && m[i] <= 'Z')
		{
			c[i] = (m[i] - 'A' - k) + 'a';
		}
		else if (m[i] >= 'A' && m[i] < 'A' + k)
		{
			c[i] = (m[i] - 'A') + ('z' + 1 - k);
		}
		else
		{
			c[i] = m[i];
		}
	}
}
//解密
void Caesar_decrypt(int k, char* c, unsigned int cLen, char* m)
{
	unsigned int i = 0;
	for (i = 0; i < cLen; i++)
	{
		if (c[i] >= 'A' + k && c[i] <= 'Z')
		{
			m[i] = (c[i] - 'A' - k) + 'a';
		}
		else if (c[i] >= 'A' && c[i] < 'A' + k)
		{
			m[i] = (c[i] - 'A') + ('z' + 1 - k);
		}
		else if (c[i] >= 'a' && c[i] <= 'z' - k)
		{
			m[i] = (c[i] - 'a') + ('A' + k);
		}
		else if (c[i] > 'z' - k && c[i] <= 'z')
		{
			m[i] = (c[i] + k - 'z' - 1) + 'A';
		}
		else
			m[i] = c[i];
	}
}

2.仿射密码

​仿射密码为单表加密的一种,字母系统中所有字母都藉一简单数学方程加密,对应至数值,或转回字母。

加密对象:英文字母

密钥:a,b。 

加密函数:E(x)=ax+b(mod m)

解密函数:D(x)=a-1*(x-b)(mod m)

※说明:1.a和26互质 b需要0~25。2.a~z对应于0~25, 英文字母对应数字。3.a-1是a关于26的乘法逆元  乘法逆元:若gcd(a,b)=1,存在c,ac ≡1 mod b,称c为a模b的乘法逆元。

仿射密码_百度百科 (baidu.com)

//放射加密函数,对字符串进行加密,
//string:明文 mlen:明文长度,a,b:密钥,c密文
void Affine_ce(char* string, int mLen, int a, int b,char*c )
{
	int i = 0;
	int k = 0;
	int code[200] = { 0 };
	for (i=0;i<mLen;i++)
	{
		k = 0;
		//printf("%c-", string[i]);
		if (string[i] <= 'z' && string[i] >= 'a')
			k = string[i] - 'a';
		else if (string[i] <= 'Z' && string[i] >= 'A')
			k = string[i] - 'A';
		else
			printf("error");
		code[i] = (k*a+b)%26;
		//printf("%d\t", code[i]);
		c[i] = 'a' + code[i];
	}
}
//因为数字比较小,用穷举法求的乘法逆元,也可以用拓展欧几里得算法
//求a模x的乘法逆元函数
int invmod(int a, int x)
{
	int i;//逐个遍历
	for (i = 1; i < x; i++)
	{
		if ((a * i )% x == 1)
			return i;
	}
	printf("没有找到");
	return -1;
}
//解密函数D(x)=a^-1(x-b)mod26
//c密文,m明文,mL长度
void Affine_de(char* c, int mL, int a, int b, char* m)
{
	int i = 0;
	int k = 0;
	for (i = 0; i<mL; i++)
	{
		k=(a*(c[i] - 'a' - b) )% 26;
		if(a * (c[i] - 'a' - b)<0)
			k= k+26;
		m[i] = 'a' + k;
	}
	return;
}

我写的时候一直解密的时候出错,看了别人的才知道,“a-1*(x-b)”是有可能是负数的!!啊!

整个代码都写的很弱智

<think>嗯,用户想了解OpenCV和仿射变换的结合使用。首先,我需要确定用户对这两个概念的基础了解程度。可能用户已经知道OpenCV是一个计算机视觉库,但仿射变换的具体细节可能需要解释。 首先,仿射变换的定义是关键。它包含线性变换和平移,保持图形的平直性和平行性。需要举一些例子,比如平移、旋转、缩放和错切,这些都属于仿射变换的范畴。然后,得说明在OpenCV中如何现这些变换,特别是使用cv2.getAffineTransform和cv2.warpAffine这两个函数。 接下来,用户可能需要具体的步骤说明。例如,如何通过三个点对来计算变换矩阵,然后用这个矩阵进行图像变换。这里需要注意输入点的正确性,以及如何选择这些点来达到预期的变换效果。 另外,可能用户会遇到际问题,比如如何调整图像位置纠正几何失真。这时候,应用仿射变换的步骤和代码示例会很有帮助。需要确保代码示例正确,且解释清楚每个参数的作用,比如src_points和dst_points的意义,以及变换后的输出尺寸。 同时,要区分仿射变换和透视变换的不同,避免用户混淆。仿射变换是2D的,保持平行线,而透视变换是3D的,可以改变消失点。这个区别在际应用中很重要,需要明确说明。 可能用户还会关心际应用场景,比如图像配准、数据增强者图像校正。这时候,举一些际例子会增强回答的用性。比如在图像处理中,如何用仿射变换来旋转缩放图像,者在校正文档时调整倾斜。 最后,需要注意LaTeX格式的要求,确保数学公式正确用$符号包裹,独立公式用$$。例如,仿射变换的矩阵表达式需要正确呈现,且行内公式如$(a_{11}, a_{12})$也要符合格式要求。 检查整个回答的结构是否清晰,步骤是否详细,代码示例是否正确,语言是否简洁易懂。确保用户能够按照步骤操作,理解仿射变换在OpenCV中的应用方法,能够应用到际项目中。</think>好的,我将逐步为您介绍OpenCV中的仿射变换,保持公式的规范排版。 ### 一、仿射变换基础概念 仿射变换(Affine Transformation)是二维平面中的线性变换+平移变换的组合,数学表达式为: $$ \begin{cases} x' = a_{11}x + a_{12}y + b_1 \\ y' = a_{21}x + a_{22}y + b_2 \end{cases} $$ 其中$(x,y)$是原坐标,$(x',y')$是变换后坐标,矩阵$A = \begin{bmatrix} a_{11} & a_{12} \\ a_{21} & a_{22} \end{bmatrix}$控制线性变换,向量$\mathbf{b} = [b_1, b_2]^T$控制平移 ### 二、OpenCV现步骤 1. **获取变换矩阵**: 使用`cv2.getAffineTransform(src_points, dst_points)` - 需要3对非共线点($2\times3$矩阵) - 例如:将三角形区域映射到新位置 2. **执行变换**: 使用`cv2.warpAffine(src, M, dsize)` - `M`是$2\times3$变换矩阵 - `dsize`指定输出图像尺寸 ### 三、核心代码示例 ```python import cv2 import numpy as np # 原始点与目标点(需为float32类型) src_points = np.float32([[50,50], [200,50], [50,200]]) dst_points = np.float32([[10,100], [200,50], [100,250]]) # 计算变换矩阵 M = cv2.getAffineTransform(src_points, dst_points) # 执行变换 img = cv2.imread('input.jpg') result = cv2.warpAffine(img, M, (cols, rows)) # cols/rows为输出尺寸 ``` ### 四、典型应用场景 1. **图像校正**:修正扫描文档的倾斜 2. **数据增强**:生成旋转/缩放后的训练样本 3. **配准对齐**:将不同视角的图像对齐到同一坐标系 4. **2D动画**:现物体的平移、旋转组合运动 ### 五、与透视变换的区别 | 特性 | 仿射变换 | 透视变换 | |-----------|----------------------|-----------------------| | 自由度 | 6个参数($2\times3$矩阵) | 8个参数($3\times3$矩阵) | | 保持性质 | 平行线保持平行 | 平行线可能相交(消失点效果) | | 数学表示 | 线性变换+平移 | 投影变换 | | OpenCV函数 | `warpAffine` | `warpPerspective` | ### 六、关键参数说明 1. 变换矩阵$M$的组成: $$ M = \begin{bmatrix} a_{11} & a_{12} & b_1 \\ a_{21} & a_{22} & b_2 \end{bmatrix} $$ 其中前两列控制旋转/缩放,最后一列控制平移 2. 旋转矩阵的特殊形式: $$ M = \begin{bmatrix} \alpha\cos\theta & -\alpha\sin\theta & t_x \\ \alpha\sin\theta & \alpha\cos\theta & t_y \end{bmatrix} $$ 这里$\theta$是旋转角度,$\alpha$是缩放因子,$(t_x, t_y)$是平移量 ### 七、常见问题处理 1. **黑边问题**:通过调整输出尺寸添加背景填充 2. **插值选择**:根据需求使用`INTER_LINEAR``INTER_NEAREST` 3. **逆变换计算**:使用`cv2.invertAffineTransform()` 建议在际使用中结合具体需求调整变换参数,可通过绘制特征点帮助确认变换效果。需要更多具体应用场景的代码示例可以进一步说明。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值