图片嵌入-大容量的信息隐藏算法

分享一下最近看到的一个关于图片嵌入隐藏的算法:

“大容量的信息隐藏算法",这是一种基于空间域的自适应多平面位的信息隐藏算法。该算法计算复杂度低、信息隐藏量大。且有实验表明在不影响图像视觉效果的前提下,其信息隐藏量比LSB算法大,并具有更高的安全性。该算法的主要思想是对每个像素点进行判断,根据HVS的特性,在最高非0有效位后的指定位(y)开始嵌入隐藏信息,嵌入到另一个指定位(z)为止。

下面直接贴上MATLAB代码和实验结果:

(1) main_ImgEmbed.m

clc;
clear all;
close all;
warning off all;

yr=4;//论文中实验得到
yg=5;
yb=3;

Img=imread(‘lena.jpg‘);
figure;imshow(Img,[]);title(‘原图‘);

Img=double(Img);
ImgR=Img(:,:,1);
ImgG=Img(:,:,2);
ImgB=Img(:,:,3);

Imgmark=imread(‘ImgEmbed.jpg‘);
Imgmark=double(Imgmark);
figure;imshow(Imgmark,[]);title(‘ImgEmbed‘);
[markm,markn]=size(Imgmark);
Imgmarkline = Imgmark(:); %二维数组转成一列

Imgmarklinebin=zeros(markm*markn*8,1); %转化为二进制
for ii=1:markm*markn
    [Imgmarklinebin(8*ii-7),Imgmarklinebin(8*ii-6),Imgmarklinebin(8*ii-5),Imgmarklinebin(8*ii-4),Imgmarklinebin(8*ii-3),...
        Imgmarklinebin(8*ii-2),Imgmarklinebin(8*ii-1),Imgmarklinebin(8*ii)]=Find8bits(Imgmarkline(ii));
end

%%
%嵌入
%对于红色通道
embedNumsed=0;%已嵌入个数
[M,N,Z]=size(Img);
y=zeros(8,1);
flag=0; %辅助跳出的标志

ImgRline=ImgR(:); %转换为一列
ImgRlineNew=ImgRline; %嵌入后
for ii=1:M*N
    if flag==1; %跳出外层循环
       break;
    end

    [y(8),y(7),y(6),y(5),y(4),y(3),y(2),y(1)]=Find8bits(ImgRline(ii));
    posNzreo=FindNotZero(y(8),y(7),y(6),y(5),y(4),y(3),y(2),y(1));
    embedNums=posNzreo-yr; %能嵌入的个数
    if  embedNums>0 %符合嵌入条件
        for jj=1:embedNums

            embedNumsed=embedNumsed+1; %已嵌入个数
            if embedNumsed>markm*markn*8 %嵌入完成
               flag=1; %设置标识,使外层循环也跳出
               break;
            end 

            y(jj)=Imgmarklinebin(embedNumsed);%嵌入
        end
    end
    ImgRlineNew(ii)=bin2dec_trans(y(8),y(7),y(6),y(5),y(4),y(3),y(2),y(1));%嵌入后的
end
ImgR2=reshape(ImgRlineNew,[M,N]);

%对于G通道
ImgGline=ImgG(:); %转换为一列
ImgGlineNew=ImgGline; %嵌入后
for ii=1:M*N
    if flag==1; %跳出外层循环
       break;
    end

    [y(8),y(7),y(6),y(5),y(4),y(3),y(2),y(1)]=Find8bits(ImgGline(ii));
    posNzreo=FindNotZero(y(8),y(7),y(6),y(5),y(4),y(3),y(2),y(1));
    embedNums=posNzreo-yg; %能嵌入的个数
    if  embedNums>0 %符合嵌入条件
        for jj=1:embedNums
            embedNumsed=embedNumsed+1; %已嵌入个数
            if embedNumsed>markm*markn*8 %嵌入完成
               flag=1; %设置标识,使外层循环也跳出
               break;
            end 

            y(jj)=Imgmarklinebin(embedNumsed);%嵌入
        end
    end
    ImgGlineNew(ii)=bin2dec_trans(y(8),y(7),y(6),y(5),y(4),y(3),y(2),y(1));%嵌入后的
end
ImgG2=reshape(ImgGlineNew,[M,N]);

%对于B通道
ImgBline=ImgB(:); %转换为一列
ImgBlineNew=ImgBline; %嵌入后
for ii=1:M*N
    if flag==1; %跳出外层循环
       break;
    end

    [y(8),y(7),y(6),y(5),y(4),y(3),y(2),y(1)]=Find8bits(ImgBline(ii));
    posNzreo=FindNotZero(y(8),y(7),y(6),y(5),y(4),y(3),y(2),y(1));
    embedNums=posNzreo-yb; %能嵌入的个数
    if  embedNums>0 %符合嵌入条件
        for jj=1:embedNums
            embedNumsed=embedNumsed+1; %已嵌入个数
            if embedNumsed>markm*markn*8 %嵌入完成
               flag=1; %设置标识,使外层循环也跳出
               break;
            end 

            y(jj)=Imgmarklinebin(embedNumsed);%嵌入
        end
    end
    ImgBlineNew(ii)=bin2dec_trans(y(8),y(7),y(6),y(5),y(4),y(3),y(2),y(1));%嵌入后的
end
ImgB2=reshape(ImgBlineNew,[M,N]);

ImgNew=zeros(M,N,Z);
ImgNew(:,:,1)=ImgR2;
ImgNew(:,:,2)=ImgG2;
ImgNew(:,:,3)=ImgB2;

figure;imshow(uint8(ImgNew),[]);title(‘嵌入后的RGB图‘);
% imwrite(uint8(ImgNew),‘介质图片_嵌入图像后.jpg‘); %保存图片

%%
%提取嵌入图像
flag=0;
Imgmark_extractlinebin=zeros(markm*markn*8,1);
extractNumsed=0;%已提取个数

% R通道
ImgRline2=ImgR2(:); %转换为一列
for ii=1:M*N
    if flag==1; %跳出外层循环
       break;
    end

    [y(8),y(7),y(6),y(5),y(4),y(3),y(2),y(1)]=Find8bits(ImgRline2(ii));
    posNzreo=FindNotZero(y(8),y(7),y(6),y(5),y(4),y(3),y(2),y(1));
    embedNums=posNzreo-yr; %已嵌入的个数
    if  embedNums>0 %符合嵌入条件
        for jj=1:embedNums

            extractNumsed=extractNumsed+1; %已提取个数
            if extractNumsed>markm*markn*8 %提取完成
               flag=1; %设置标识,使外层循环也跳出
               break;
            end 

           Imgmark_extractlinebin(extractNumsed)=y(jj);%提取
        end
    end
end

% G通道
ImgGline2=ImgG2(:); %转换为一列
for ii=1:M*N
    if flag==1; %跳出外层循环
       break;
    end

    [y(8),y(7),y(6),y(5),y(4),y(3),y(2),y(1)]=Find8bits(ImgGline2(ii));
    posNzreo=FindNotZero(y(8),y(7),y(6),y(5),y(4),y(3),y(2),y(1));
    embedNums=posNzreo-yg; %已嵌入的个数
    if  embedNums>0 %符合嵌入条件
        for jj=1:embedNums

            extractNumsed=extractNumsed+1; %已提取个数
            if extractNumsed>markm*markn*8 %提取完成
               flag=1; %设置标识,使外层循环也跳出
               break;
            end 

           Imgmark_extractlinebin(extractNumsed)=y(jj);%提取
        end
    end
end

% G通道
ImgBline2=ImgB2(:); %转换为一列
for ii=1:M*N
    if flag==1; %跳出外层循环
       break;
    end

    [y(8),y(7),y(6),y(5),y(4),y(3),y(2),y(1)]=Find8bits(ImgBline2(ii));
    posNzreo=FindNotZero(y(8),y(7),y(6),y(5),y(4),y(3),y(2),y(1));
    embedNums=posNzreo-yb; %已嵌入的个数
    if  embedNums>0 %符合嵌入条件
        for jj=1:embedNums

            extractNumsed=extractNumsed+1; %已提取个数
            if extractNumsed>markm*markn*8 %提取完成
               flag=1; %设置标识,使外层循环也跳出
               break;
            end 

           Imgmark_extractlinebin(extractNumsed)=y(jj);%提取
        end
    end
end

%二进制转十进制
Imgmarklinedec=zeros(markm*markn,1); %转化为十进制
for ii=1:markm*markn
    Imgmarklinedec(ii)=bin2dec_trans(Imgmark_extractlinebin(8*ii-7),Imgmark_extractlinebin(8*ii-6),Imgmark_extractlinebin(8*ii-5),Imgmark_extractlinebin(8*ii-4),...
                                     Imgmark_extractlinebin(8*ii-3),Imgmark_extractlinebin(8*ii-2),Imgmark_extractlinebin(8*ii-1),Imgmark_extractlinebin(8*ii));
end
Imgmarkextract=reshape(Imgmarklinedec,[markm,markn]);
figure;imshow(Imgmarkextract,[]);title(‘提取的嵌入图片‘);
% imwrite(uint8(Imgmarkextract),‘待嵌入图片_gray_提取结果.jpg‘); %保存图片

%检查提取的水印和原水印的区别
difmarked=Imgmarkextract-Imgmark; %做差
%发现差为0,即说明完全一致,提取正确

(2)Find8bits.m

function [y7,y6,y5,y4,y3,y2,y1,y0]=Find8bits(Data)
y0=mod(Data,2);
y7=fix(Data/128);Data=Data-y7*128;
y6=fix(Data/64); Data=Data-y6*64;
y5=fix(Data/32); Data=Data-y5*32;
y4=fix(Data/16); Data=Data-y4*16;
y3=fix(Data/8);  Data=Data-y3*8;
y2=fix(Data/4);  Data=Data-y2*4;
y1=fix(Data/2);  Data=Data-y1*2;
end

 

(3)bin2dec_trans.m 

%二进制转十进制
function Data=bin2dec_trans(y7,y6,y5,y4,y3,y2,y1,y0)
   Data=y7*128+y6*64+y5*32+y4*16+y3*8+y2*4+y1*2+y0;
end

  

(4)FindNotZero.m

%找出第一个不为零的数位 从最高位(第八位)开始
function posNzreo=FindNotZero(y7,y6,y5,y4,y3,y2,y1,y0)
if y7~=0      posNzreo=8;
elseif y6~=0  posNzreo=7;
elseif y5~=0  posNzreo=6;
elseif y4~=0  posNzreo=5;
elseif y3~=0  posNzreo=4;
elseif y2~=0  posNzreo=3;
elseif y1~=0  posNzreo=2;
else          posNzreo=1;
end
end

  

实验结果如下:

(1)原图

(2)要嵌入隐藏的图片

(3)嵌入隐藏图片后的介质图像

(4)提取的嵌入图片

整个工程代码下载请到:http://download.csdn.net/download/tianma5/9508467

才疏学浅,多多指教。

时间: 2024-07-30 03:50:54

图片嵌入-大容量的信息隐藏算法的相关文章

二值信息隐藏(分块和游程编码实现)

使用分块进行信息隐藏,因为在对角线上的分块上进行的隐藏,所以 可以明显看到在对角线上有一条线, 200*200的二值图像 512*512的二值图像 (二)使用游程编码,书上的代码逻辑上有错误,还有一些函数错误,根本不能运行出结果 自己修改了得到以下结果 200*200的隐藏160位,可以看到微小的变化 512*512的隐藏160位,基本看不到变化 二值对角线分块隐藏代码 clc; clear; msgfid = fopen('hidden.txt','r'); % 隐藏信息 [msg, coun

使用ueditor时候修改图片路径及其相关信息

ueditor功能比较强大  使用也比较方便 但是有一些东西是需要我们自己根据实际情况去设置的 以下是关于图片/涂鸦/视频等上传信息的更改: 首先我们要找到配置文件config.json 注意不是config.json.js 路径如下: 找到配置文件后打开,可以看到如下信息: 这里可以修改图片上传的信息,比如图片最大限制,图片格式,图片路径等问题.... 因为默认是保存在根目录下的ueditor下的  我这里我保存在了mymessystem文件加下  文件名仍用默认的  也可以自己修改 但是应该

使用freemaker 导出word 含多张图片,若无图片则显示文本信息

1.使用的Microsoft Office 2007,添加一个无边框的表格,并插入一张图片,最后另存为编码utf-8,一开始保存的word xml格式的,图片的base64编码位于文档最后,暂时没有找到解决方法,所以就保存. 2.用编辑工具打开,找到base64编码替换为ftl标签,红色所示,图片设置长宽(蓝色所示) <w:p wsp:rsidR="00A50283" wsp:rsidRDefault="00A50283" wsp:rsidP="00

W5500 图片嵌入STM32 FLASH笔记(备忘)

方法一:利用winHex软件将图片转为16进制数组存储在FALSH中 1 __root const char HDMV_HTML[]="<html>" 2 "<head>" 3 "<meta http-equiv='Content-Type' content='text/html; charset=utf-8' />" 4 "<!-- TemplateBeginEditable name='do

不用第三方解码库取得图片宽高 附完整C++算法实现代码

在特定的应用场景下,有时候我们只是想获取图片的宽高, 但不想通过解码图片才取得这个信息. 预先知道图片的宽高信息,进而提速图片加载,预处理等相关操作以提升体验. 在stackoverflow有一篇相关讨论. Get Image size WITHOUT loading image into memoryhttp://stackoverflow.com/questions/15800704/python-get-image-size-without-loading-image-into-memor

将图片嵌入到markdown文档中

转自KFXW的专栏 将图片嵌入Markdown文档中一直是一个比较麻烦的事情.通常的做法是将图片存入本地某个路径或者网络存储空间,使用URL链接的形式插入图片: ![image][url_to_image] 这样做一个明显的麻烦之处在于处理图片与Markdown文档的一致性上.如果我们要拷贝文档,或者图片遭到误删/云端链接失效,就会变得不便.最让我们省心的方法便是将图片直接放到文档内部. 一个将图片嵌入文档中的方法是使用base64编码.步骤比较简单: 1. 将图片或截图保存在本地: 2. 使用

01将图片嵌入到Markdown文档中

将图片内嵌入Markdown文档中 将图片嵌入Markdown文档中一直是一个比较麻烦的事情.通常的做法是将图片存入本地某个路径或者网络存储空间,使用URL链接的形式插入图片: ![image][url_to_image] 这样做一个明显的麻烦之处在于处理图片与Markdown文档的一致性上.如果我们要拷贝文档,或者图片遭到误删/云端链接失效,就会变得不便.最让我们省心的方法便是将图片直接放到文档内部. 一个将图片嵌入文档中的方法是使用base64编码.步骤比较简单: 将图片或截图保存在本地:

(转)从信息隐藏的一个需求看C++接口与实现的分离

原文地址https://blog.csdn.net/tonywearme/article/details/6926649 让我们从stackoverflow上一个同学的问题来开始.问题的原型是这样的(原问题见:class member privacy and headers in C++):Portaljacker:"有一个类A, 有一些共有成员函数和私有数据,如下所示." class A{public: X getX(); Y getY(); Z getZ(); .. private

Web应用程序的敏感信息-隐藏目录和文件

Web应用程序的敏感信息-隐藏目录和文件 0x1.场景 Web应用程序根文件夹中可能存在大量隐藏信息:源代码版本系统文件夹和文件(.git,.gitignore,.svn),项目配置文件(.npmrc,package.json,.htaccess),自定义配置文件使用config.json,config.yml,config.xml等常见扩展以及许多其他扩展. 资源可以分为几个常见类别: 源代码版本控制系统 IDE(集成开发环境)配置文件 项目和/或技术特定的配置和设置文件 1.1.GIT Gi