光线补偿

原文讲解不清,特修改一下。。
    在图片的整体颜色偏暗或偏亮时,需要采用光线补偿的方法调整图片颜色。普遍采用光线补偿方法的是HsuRL在《Face detection in color images》中提出的可变光照及复杂背景下的肤色检测算法。
    具体做法是检测图像中亮度在前5%的像素(参考白),按一定公式计算出调整值,则对图像的RGB三个分量进行线性调整,如果整张图片较暗,前5%平均灰度值会比255较小,调整值较大,把整个图片的颜色调亮.

HsuRL《Face detection in color images》论文下载地址 http://www.51xuewen.com/res/show.aspx?resid=2453 = 0;
unsigned char RedTemp,GreenTemp,BlueTemp;

for (j=y1; j<y2; j++) {
    for (i=x1; i<x2; i++) {
      index = VL_RGB_PIXEL * (j*width + i);
    
   //得到rgb值
    RedTemp=input[index];
          GreenTemp=input[index+1];
          BlueTemp=input[index+2];
   //计算灰度值
   int gray = (RedTemp * 299 + GreenTemp * 587 + BlueTemp * 114)/1000;
   histogram[gray]++;
}
}
int calnum =0;
  int total = x2 * y2;
  int num;
  //下面的循环得到满足系数thresholdco的临界灰度级
  for(i =0;i<256;i++)
  {
   if((float)calnum/total < thresholdco) //得到前5%的高亮像素
   {
    calnum+= histogram[255-i];//histogram保存的是某一灰度值的像素个数,calnum是边界灰度之上的像素数
    num = i;
   }
   else
    break;
  }
  int averagegray = 0;
  calnum =0;
  //得到满足条件的象素总的灰度值
  for(i = 255;i>=255-num;i--)
  {
   averagegray += histogram[i]
*i;//总的像素的个数*灰度值
   calnum += histogram[i]
;//总的像素数
  }
  averagegray /=calnum;
  //得到光线补偿的系数
  float co = 255.0/(float)averagegray
;
  //下面的循环对图象进行光线补偿
for (j=y1; j<y2; j++) {
      for (i=x1; i<x2; i++)
   {
    //得到数据偏移
       index = VL_RGB_PIXEL * (j*width + i);
    //得到分量
       for(int n=0;n<3;n++)
    {
    int nTemp=input[index+n]*co;
    output[index+n]=(nTemp>255)?255:nTemp;
    
    }  }  }


核心代码:
const float thresholdco = 0.05;
//象素个数的临界常数
const int thresholdnum = 100;
//灰度级数组
int histogram[256];
for(i =0;i<256;i++)
  histogram
至此,我还有一点疑问:这个的数学原理是什么呢?虽然的确有效果。。
原文解释:
2009080117451266.jpg

另外一种补偿方法是东南大学夏思宇博士在一种改进的自适应肤色检测算法》(链接中提供此论文的万方站点下载地址,免费的没找到。呵呵中提出的用白平衡算法代替HsuRl的光线补偿方法,能较好的解决由光照引起的图像彩色偏移,使得检测结果更加稳健。白平衡会按目前图像中的图像特性,调整整个图像红绿蓝强度,以修正外部光线所造成的误差,平衡就是不考虑环境光线,让系统默认“白色”,就是让他能认出白色,而平衡其他颜色在有色光线下的色调。计算步骤如下:
1.计算图像的R,G,B分量的各自平均值R',G',B',并令图像的平均灰度值avgGray=(G'+R'+B')/3.
2.令Kr=avgGray/R',Kg=avgGray/G',Kb=avgGray/B',调整每个像素点的RGB值R=R*Kr,G=G*Kg,B=B*Kb,并处理越界情况,将大于255的值置为255
代码:
int RedTotal=0,GreenTotal=0,BlueTotal=0,NumTotal,GrayTotal,RedTemp,GreenTemp,BlueTemp;
  unsigned char RedAverage,GreenAverage,BlueAverage,GrayAverage;
  
  float Kr,Kg,Kb;
  for (j=y1; j<y2; j++) {
    for (i=x1; i<x2; i++) {
      index = VL_RGB_PIXEL * (j*width + i);
     //得到rgb值
    RedTotal+=input[index];
          GreenTotal+=input[index+1];
          BlueTotal+=input[index+2];
   //计算灰度值
    //GrayTotal = (input[index] * 299 + input[index+1] * 587 + input[index+2] * 114)/1000;
  
}
}
    NumTotal=x2 * y2;
    RedAverage=RedTotal/NumTotal;
GreenAverage=GreenTotal/NumTotal;
BlueAverage=BlueTotal/NumTotal;
GrayAverage=(RedAverage+GreenAverage+BlueAverage)/3;
Kr=(float)GrayAverage/(RedAverage);
Kg=(float)GrayAverage/(GreenAverage);
Kb=(float)GrayAverage/(BlueAverage);
for (j=y1; j<y2; j++) {
    for (i=x1; i<x2; i++) {
      index = VL_RGB_PIXEL * (j*width + i);
      RedTemp=input[index] * Kr;
   GreenTemp=input[index+1] * Kg;
   BlueTemp=input[index+2] * Kb;
    output[index]=(RedTemp>255) ? 255 : RedTemp;
    output[index+1]=(GreenTemp>255) ? 255 : GreenTemp;
    output[index+2]=(BlueTemp>255) ? 255 : BlueTemp;
    
}
}
它的补偿效果有待进一步验证

 

转载于:https://www.cnblogs.com/oskycar/archive/2009/07/31/1536229.html

  • 1
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值