求用opencv识别红色区域 并定位的具体流程!!!

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了求用opencv识别红色区域 并定位的具体流程!!!相关的知识,希望对你有一定的参考价值。

参考技术A 直接对每个像素点判断即可,src是图像
IplImage* src;
CvScalar s;
for(int i = 0;i < src->height;i++)

for(int j = 0;j < src->width;j++)


s = cvGet2D(src,i,j); // 获得像素值
if(s.val[0]<50&&s.val[1]<50&&s.val[2]>200)
//注意这里的012对应的是bgr,范围的意思是防止光线的明暗影响,可以适当放宽,另外你也可以选择其他的颜色空间,可以直接取消明暗影响,比如HSV

s.val[0]=0;
s.val[1]=0;
s.val[2]=255;
//如果满足条件就设置为红色
else

s.val[0]=0;
s.val[1]=0;
s.val[2]=0;
//如果不满足就设置为黑色
cvSet2D(src,i,j,s); //设置像素


cvNamedWindow( "image", 1 );
cvShowImage("image",src); //显示出来
另外你说的定位是什么意思,是不是说像车牌那样做一个矩形框框起来?我这做过一个车牌定位的,如果是的话我可以发给你!或者把代码贴出来追问

要不要转到灰度图像啊! 不是要对它进行滤波和 腐蚀吗?这样子效果会更好!

如果想对它 进行 滤波和腐蚀的 该怎么做啊?

追答

下面接着写:
IplImage* dst_gray;
dst_gray=cvCreateImage(cvGetSize(src),8,1);
cvCvtColor(src,dst_gray,CV_BGR2GRAY);
//对图像进行自适二值化
BinarizeImageByOTSU(dst_gray);
//图像膨胀
cvDilate(dst_gray,dst_gray);
//图像腐蚀
cvErode(dst_gray,dst_gray);
//在二值图像中寻找轮廓
cvFindContours( dst_gray, storage, &contour, sizeof(CvContour), CV_RETR_CCOMP, CV_CHAIN_APPROX_SIMPLE );
cvZero( dst );//清空数组
cvCvtColor(dst_gray,dst,CV_GRAY2BGR);

这样基本处理就都完成了(注:上面的膨胀腐蚀可以自己去调整次数)!

追问

要是 转到HSV空间的话? 怎么选出红色,并让别的颜色都变黑! 还有啊。有办法克服光线的影响吗?光线一变化,感觉效果就差很远!

追答

用HSV是可以除去光线影响的,两个颜色体系有个公式,你百度一下就知道了!

追问

但是我发现在处理视频帧的时候 用HSV 会变得很卡

追答

那个公式貌似不复杂的,那么看来是你的机器不够快吧,毕竟视频跟图像是不太一样的,其实你可以不要每一帧都处理,你可以隔多少帧处理一次,这样可能好些,另外,要是实在不行的话就用rgb的吧,把判断的条件稍微放宽些。

追问

识别出轮廓后,该怎么求轮廓的质心坐标啊!

追答

看你的意思是任意轮廓啊,那么就遍历轮廓,我记得均匀材质的二维图形的质心的坐标好像是积分求平均值吧,比如x坐标是所有点的x坐标的平均值。

本回答被提问者采纳

opencv 验证码 识别

示例图片 :  技术分享图片

 

主要应用原理为:1

1、先识别出图片中每个像素的数量   例如 红色在200左右

2、将红色的像素单独提出来  这样起到去除噪点的作用

3、分割图片并保存  

4、识别图片

 

具体代码如下:

  1 # coding=utf-8
  2 # !/usr/bin/python
  3 """
  4 opencv 验证码识别
  5 Created on: 2018/7/31  16:12
  6 @author: 虫子慢慢爬
  7 Email: [email protected]
  8 """
  9 # -*- coding=GBK -*-
 10 
 11 from PIL import Image
 12 import hashlib
 13 import time
 14 
 15 im = Image.open("C:/Users/admin/Desktop/image/p.jpg")
 16 
 17 # (将图片转换为8位像素模式)
 18 
 19 im = im.convert("P")
 20 
 21 # 打印颜色直方图
 22 
 23 print(im.histogram())
 24 """颜色直方图的每一位数字都代表了在图片中含有对应位的颜色的像素的数量。
 25 ?? 每个像素点可表现256种颜色,你会发现白点是最多
 26    (白色序号255的位置,也就是最后一位,可以看到,有625个白色像素)。
 27    红像素在序号200左右,我们可以通过排序,得到有用的颜色。
 28 """
 29 his = im.histogram()
 30 
 31 values = {}
 32 
 33 for i in range(256):
 34     values[i] = his[i]
 35 
 36 for j, k in sorted(values.items(), key=lambda x: x[1], reverse=True)[:10]:
 37     print(j, k)
 38 """
 39 我们得到了图片中最多的10种颜色,
 40 其中 220 与 227 才是我们需要的红色和灰色,
 41 可以通过这一讯息构造一种黑白二值图片
 42 """
 43 im2 = Image.new("P", im.size, 255)
 44 
 45 for x in range(im.size[1]):
 46 
 47     for y in range(im.size[0]):
 48         pix = im.getpixel((y, x))
 49         if pix == 225:  # these are the numbers to get
 50             im2.putpixel((y, x), 0)
 51 
 52 im2.show()
 53 # time.sleep(3)
 54 """?接下来的工作是要得到单个字符的像素集合,由于例子比较简单,我们对其进行纵向切割:"""
 55 
 56 inletter = False
 57 
 58 foundletter = False
 59 
 60 start = 0
 61 
 62 end = 0
 63 
 64 letters = []
 65 
 66 for y in range(im2.size[0]):
 67 
 68     for x in range(im2.size[1]):
 69         pix = im2.getpixel((y, x))
 70 
 71         if pix != 255:
 72             inletter = True
 73 
 74     if foundletter == False and inletter == True:
 75         foundletter = True
 76         start = y
 77 
 78     if foundletter == True and inletter == False:
 79         foundletter = False
 80         end = y
 81         letters.append((start, end))
 82 
 83     inletter = False
 84 
 85 print(letters)
 86 
 87 # [(6, 14), (15, 25), (27, 35), (37, 46), (48, 56), (57, 67)]
 88 
 89 """??得到每个字符开始和结束的列序号。"""
 90 
 91 count = 0
 92 
 93 for letter in letters:
 94     m = hashlib.md5()
 95 
 96     im3 = im2.crop((letter[0], 0, letter[1], im2.size[1]))
 97     ss1 = str(time.time()) + str(count)
 98     print(ss1)
 99     m.update(ss1.encode(utf-8))
100     # 对图片进行切割,得到每个字符所在的那部分图片。
101     im3.save("./%s.gif" % (m.hexdigest()))
102 
103     count += 1
104     """
105 在这里我们使用向量空间搜索引擎来做字符识别,它具有很多优点:
106 
107 不需要大量的训练迭代
108 
109 不会训练过度
110 
111 你可以随时加入/移除错误的数据查看效果
112 
113 很容易理解和编写成代码
114 
115 提供分级结果,你可以查看最接近的多个匹配
116 
117 对于无法识别的东西只要加入到搜索引擎中,马上就能识别了。
118 
119 ??当然它也有缺点,例如分类的速度比神经网络慢很多,它不能找到自己的方法解决问题等等。
120 
121 ??向量空间搜索引擎名字听上去很高大上其实原理很简单。拿文章里的例子来说:
122 
123 ??你有 3 篇文档,我们要怎么计算它们之间的相似度呢?两篇文档所使用的相同的单词越多,那这两篇文章就越相似!但是这单词太多怎么办,就由我们来选择几个关键单词,选择的单词又被称作特征,每一个特征就好比空间中的一个维度(x,y,z 等),一组特征就是一个矢量,每一个文档我们都能得到这么一个矢量,只要计算矢量之间的夹角就能得到文章的相似度了。
124 
125 ??用 Python 类实现向量空间:
126 """
127 
128 import math
129 
130 
131 class VectorCompare:
132 
133     # 计算矢量大小
134 
135     def magnitude(self, concordance):
136 
137         total = 0
138 
139         for word, count in concordance.iteritems():
140             total += count ** 2
141 
142         return math.sqrt(total)
143 
144     # 计算矢量之间的 cos 值
145 
146     def relation(self, concordance1, concordance2):
147 
148         relevance = 0
149 
150         topvalue = 0
151 
152         for word, count in concordance1.iteritems():
153 
154             if concordance2.has_key(word):
155                 topvalue += count * concordance2[word]
156 
157         return topvalue / (self.magnitude(concordance1) * self.magnitude(concordance2))
158 
159     # ??它会比较两个 python 字典类型并输出它们的相似度(用 0~1 的数字表示)
160 
161     """
162     将之前的内容放在一起
163     ??还有取大量验证码提取单个字符图片作为训练集合的工作,但只要是有好好读上文的同学就一定知道这些工作要怎么做,在这里就略去了。可以直接使用提供的训练集合来进行下面的操作。
164     
165     ??iconset目录下放的是我们的训练集。
166     
167     ??最后追加的内容:
168     
169     """
170 
171     # 将图片转换为矢量
172 
173     def buildvector(im):
174 
175         d1 = {}
176 
177         count = 0
178 
179         for i in im.getdata():
180             d1[count] = i
181 
182             count += 1
183 
184         return d1
185 
186 
187 v = VectorCompare()
188 
189 iconset = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, a, b, c, d, e, f, g, h, i, j, k,
190            l, m, n, o, p, q, r, s, t, u, v, w, x, y, z]
191 
192 import os
193 
194 # 加载训练集
195 
196 imageset = []
197 
198 for letter in iconset:
199 
200     for img in os.listdir(./iconset/%s/ % (letter)):
201 
202         temp = []
203 
204         if img != "Thumbs.db" and img != ".DS_Store":
205             temp.append(v.buildvector(Image.open("./iconset/%s/%s" % (letter, img))))
206 
207             imageset.append({letter: temp})
208 
209 count = 0
210 
211 # 对验证码图片进行切割
212 
213 for letter in letters:
214     m = hashlib.md5()
215 
216     im3 = im2.crop((letter[0], 0, letter[1], im2.size[1]))
217 
218     guess = []
219 
220 # 将切割得到的验证码小片段与每个训练片段进行比较
221 
222 for image in imageset:
223 
224     for x, y in image.iteritems():
225 
226         if len(y) != 0:
227             guess.append((v.relation(y[0], v.buildvector(im3)), x))
228 
229         guess.sort(reverse=True)
230 
231     print("", guess[0])
232 
233     count += 1

 

希望对大家有帮助哦!!

以上是关于求用opencv识别红色区域 并定位的具体流程!!!的主要内容,如果未能解决你的问题,请参考以下文章

opencv 怎么识别出红色物体呀

opencv 验证码 识别

OpenCV+Python识别车牌和字符分割

opencv 颜色识别hsv方法 C++(红色)

人脸识别《一》opencv人脸识别之人脸检测

数字图像处理--车牌识别