数字图像水印


1.实验目的

(1)了解频域水印的特点

(2)掌握基于DCT系数关系的图像水印算法原理

2.实验内容(二选一)

(1)DCT域的图像水印嵌入与提取

(2)完全脆弱图像水印实验

3.实验原理

(1)DCT域的图像水印嵌入与提取

    在信号的频域(变换域)中隐藏信息要比在时域中嵌入信息具有更好的鲁棒性。一副图像经过时域到频域的变换后,可将待隐藏信息藏入图像的显著区域,这种方法比 LSB 以及其他一些时域水印算法更具抗攻击能力,而且还保持了对人类感官的不可察觉性。常用的变换域方法有离散余弦变换(DCT)、离散小波变换(DWT)和离散傅里叶变换(DFT)等。
    本章介绍一种提取秘密信息的时候不需要原始图像的盲水印算法,算法的思想是利用载体中两个特定DCT 系数的相对大小来表示隐藏的信息。载体图像分为 8×8 分块,进行二维 DCT 变换,分别选择其中的两个位置,比如用(u1,v1)和(u2,v2)代表所选定的两个系数的坐标。如果 Bi(u1,v1) < Bi(u2,v2),代表隐藏 1,如果相反,则交换两系数,如果 Bi(u1,v1) > Bi(u2,v2),代表隐藏 0,如果相反,则交换两系数。提取的时候接收者对包含水印的图像文件进行二维 DCT 变换,比较每一块中约定位置的 DCT 系数值,根据其相对大小,得到隐藏信息的比特串,从而恢复出秘密信息。但是在使用上述算法的过程中,一般都是引入一个 Alpha 变量对系数的差值进行控制,将两个系数的差别方法,可以保证提取秘密信息的正确性。

(2)完全脆弱图像水印实验

    在保证多媒体信息一定感知质量的前提下,将数字、序列号、文字、图像标志等作为数字水印嵌入到多媒体数据中,当多媒体内容受到怀疑时,可将该水印提取出来用于多媒体内容的真伪识别,并指出篡改位置,甚至攻击类型等。这种水印称为脆弱性水印,脆弱性水印分为完全脆弱性水印和半脆弱性水印。当原始载体内容发生改变时,被嵌入的水印信息就遭到了破坏,因此图像的接收方就不能完整的提取水印信息。从而可以鉴定原始数据是否被篡改。完全脆弱水印主要用于完整性保护,图像不能发生任何修改,图像如果发生一个比特的修改都会影响水印信息的提取。而半脆弱水印对一般图像处理(如:滤波、加噪声、替换、压缩等)有较强的免疫能力(鲁棒性),但是能检测到对图像的恶意篡改,一般用于内容保护。
    完全脆弱水印系统要求图像的任何部分均不能被修改,检测器对图像任何细微的变动都会做出拒绝判决。完全脆弱水印一般是从空域 LSB 水印算法演变过来,其中最具有代表性的是校验和(checksum)算法、公钥认证水印算法和查找表水印算法。
    本节介绍的算法的原理如下:校验和算法首先计算每个像素字节最高 7 位的 checksum 值,checksum 值定义为一系列相同长度数据的二进制位的模 2 和。在该算法中,此长度为 8 个连续像素中的最高 7 位的联合长度,共 56 位。在 checksum 值计算过程中,整幅图像中的每个像素都参与计算,但每个像素只计算一次,最后结果为 56 位的数据。该算法随后在图像中随机选取 56 个像素,将每个像素的最低位变为与上述checksum 比特位相同,以此存储 checksum 值,从而完成水印的嵌入。图像认证时,只需要将被检图像的checksum 值与提取的水印信息进行比较,便可得知图像是否被篡改。
    在这个算法中,随机选取的存访 checksum 值的像素位置以及 checksum 值本身构成了水印信息。在提取水印时,只需计算图像的 checksum 值并与水印信息中的 checksum 值进行比较,便可知水印是否因遭受篡改而被破坏。

4.实验记录

(1)完全脆弱图像水印实验

1)Checksum水印嵌入

cuiruoshuiyin.m源代码:(自定义一个函数)

function [row,col]=cuiruoshuiyin(omatrix,count,key)     %定义一个函数
[m,n]=size(omatrix);
distance1=ceil(m*n/count);          %朝正无穷的方向取整数
distance2=distance1-2;
if distance2==0
    error('载体太小');
end
rand('state',key);
a=rand(1,count);
row=zeros([1 count]);
col=zeros([1 count]);
r=1;
c=1;
row(1,1)=r;
col(1,1)=c;
for i=2:count
    if a(i)>=0.5
        c=c+distance1;
    else
        c=c+distance2;
    end
    if c>n
        r=r+1;
        if r>m
            error('载体太小');
        end
        c=mod(c,n);
        if c==0
            c=1;
        end
    end
    row(1,i)=r;
    col(1,i)=c;
end

checksum.m源代码:(嵌入水印)

clc;
clear;
oi=imread('dream.png');
[orow,ocol]=size(oi);
pixelcount=orow*ocol;       %计算总像素个数
count=floor(pixelcount/8);      %将总像素分为8个一组
wi=oi(:);
for i=1:count           %用于存放56bit
    for j=1:56
        l(i,j)=uint8(0);
    end
end
k=1;
i=1;
for i=1:count
    wherestart=8*(i-1);
    for j=1:8
        b(i,j)=wi(wherestart+j);
    end
end

%把每个像素值的高7位取出,顺序为2,3,4,5,6,7,8
modcount=1;
for i=1:count
    for j=1:8
        for k=1:7
            l(i,7*(j-1)+k)=bitget(b(i,j),k+1);      %由低位到高位输出,取第k+1位
            modcount=modcount+1;
        end
    end
end

%把所有的56位的值按照模2加的到一个56位长度的checksum值
for i=1:count-1
    for j=1:56
        sum(1,j)=xor(l(i,j),l(i+1,j));
    end
end

%从图像中随机选取56个像素点
key=123;        %用户选取随机嵌入的位置
sum=uint8(sum);
[row col] = cuiruoshuiyin(oi,56,key);
for k=1:56
    bitset(oi(row(k),col(k)),1,sum(1,k));
end
imwrite(oi,'watermarke.png','png');
figure;     %显示原图和添加水印信息后的图
subplot(1,2,1);     %显示的位置
imshow('dream.png');        %显示的图像
title('原始图像');      %图像的标题
subplot(1,2,2);
imshow('watermarke.png');
title('添加水印信息后的图像');

图1-1 完全脆弱水印嵌入前后对比

2)判断图像是否被修改

extractwatermark.m源代码:

clc;
clear;
oi=imread('dream.png');
[orow ocol]=size(oi);
pixelcount=orow*ocol;       %计算总像素个数
count=floor(pixelcount/8);      %总像素分为8个一组
wi=oi(:);
for i=1:count       %用于存放56比特
    for j=1:56
        l(i,j)=uint8(0);
    end
end
k=1;
i=1;
for i=1:count
    wherestart=8*(i-1);
    for j=1:8
        b(i,j)=wi(wherestart+j);
    end
end
%把每个像素值的高7位取出,顺序为2、3、4、5、6、7、8
modcount=1;
for i=1:count
    for j=1:8
        for k=1:7
            l(i,7*(j-1)+k)=bitget(b(i,j),k+1);
            modcount=modcount+1;
        end
    end
end

%把所有的56位的值按照模2加的到一个56位长度的checksum值
for i=1:count-1
    for j=1:56
        sum(1,j)=xor(l(i,j),l(i+1,j));
    end
end

%从图像中随机选取56个像素点
key=123;    %用户选取随机嵌入的位置
for k=1:56
    watermark(1,k)=0;
end
[row col]=cuiruoshuiyin(oi,56,key);
for k=1:56
    watermark(1,k)=bitget(oi(row(k),col(k)),1);
end
for k=1:56
    diff(1,k)=sum(1,k)-watermark(1,k);
end
for k=1:56
    if diff(1,k)~=0
        modified=1;
    else
        modified=0;
    end
end

图2-1 运行结果

3)判断图像是否被篡改

modpic.m源代码:

clc;
clear;
oi=imread('watermarke.png');    %读入图像
[orow ocol]=size(oi);
pixelcount=orow*ocol;   %计算总像素个数
count=floor(pixelcount/8);  %总像素分为8个一组
for i=1:10
    for j=1:10
        oi(i,j)=0;
    end
end
imwrite(oi,'watermarke.png','png');     %画出图像
figure;
subplot(1,2,1);
imshow('dream.png');
title('原始图像');
subplot(1,2,2);
imshow('watermarke.png');
title('被篡改的图像');

图3-1 原始图像与被篡改图像的对比


免责声明!

本站转载的文章为个人学习借鉴使用,本站对版权不负任何法律责任。如果侵犯了您的隐私权益,请联系本站邮箱yoyou2525@163.com删除。



 
粤ICP备18138465号  © 2018-2025 CODEPRJ.COM