搜索
首页后端开发php教程PHP之验证码识别,php验证码_PHP教程

PHP之验证码识别,php验证码

首先推荐几篇有关验证码识别的文章,觉得不错

php实现验证码的识别(初级篇)

关于bp神经网格识别验证码

一、思路

碰见一个验证码,如果我们想要识别它,我们需要的是做什么呢?
我们先观察几个验证码............


我们用人眼去观察,会很显然的认出验证码所包含的字符,那么人眼的“识别机理”是什么呢?
大概是验证码图片字符的背景的颜色区别吧,试想,如果字符和背景没有颜色区别,我们能够判断验证码吗,很显然不能。

所以,我们就可以从人出发。

先从图片的颜色着手,即图片的RGB信息。

RGB色彩模式是工业界的一种颜色标准,是通过对红(R)、绿(G)、蓝(B)三个颜色通道的变化以及它们相互之间的叠加来得到各式各样的颜色的,RGB即是代表红、绿、蓝三个通道的颜色,这个标准几乎包括了人类视力所能感知的所有颜色,是目前运用最广的颜色系统之一。

定义函数取得RGB信息

<span> 1</span> <span>//</span><span>代码本来是一个类,现在拆开来写的,有可能有不严谨的地方,大家可以看得懂就好了</span>
<span> 2</span> 
<span> 3</span> <span>/*</span>
<span> 4</span> <span> *取得图片路径和图片尺寸
</span><span> 5</span>  <span>*/</span>
<span> 6</span> <span>$this</span>->ImagePath = <span>$Image</span><span>;
</span><span> 7</span> <span>$this</span>->ImageSize = <span>getimagesize</span>(<span>$Image</span><span>);
</span><span> 8</span> 
<span> 9</span> <span>/*</span>
<span>10</span> <span> *获取图像标识符,保存到ImageInfo,只能处理bmp,png,jpg图片
</span><span>11</span> <span> *ImageCreateFromBmp是我自己定义的函数,最后会给出
</span><span>12</span>  <span>*/</span>
<span>13</span> <span>function</span><span> getInfo(){
</span><span>14</span>     <span>$filetype</span> = <span>substr</span>(<span>$this</span>->ImagePath,-3<span>);
</span><span>15</span>     <span>if</span>(<span>$filetype</span> == 'bmp'<span>){
</span><span>16</span>         <span>$this</span>->ImageInfo = <span>$this</span>->ImageCreateFromBmp(<span>$this</span>-><span>ImagePath);
</span><span>17</span>     }<span>elseif</span>(<span>$filetype</span> == 'jpg'<span>){
</span><span>18</span>         <span>$this</span>->ImageInfo = imagecreatefromjpeg(<span>$this</span>-><span>ImagePath);    
</span><span>19</span>     }<span>elseif</span>(<span>$filetype</span> == 'png'<span>){
</span><span>20</span>         <span>$this</span>->ImageInfo = imagecreatefrompng(<span>$this</span>-><span>ImagePath);    
</span><span>21</span> <span>    }
</span><span>22</span> <span>}
</span><span>23</span> 
<span>24</span> <span>/*</span><span>获取图片RGB信息</span><span>*/</span>
<span>25</span> <span>function</span><span> getRgb(){
</span><span>26</span>     <span>$rgbArray</span> = <span>array</span><span>();
</span><span>27</span>     <span>$res</span> = <span>$this</span>-><span>ImageInfo;
</span><span>28</span>     <span>$size</span> = <span>$this</span>-><span>ImageSize;
</span><span>29</span>     <span>$wid</span> = <span>$size</span>['0'<span>];
</span><span>30</span>     <span>$hid</span> = <span>$size</span>['1'<span>];
</span><span>31</span>     <span>for</span>(<span>$i</span>=0; <span>$i</span> < <span>$hid</span>; ++<span>$i</span><span>){
</span><span>32</span>         <span>for</span>(<span>$j</span>=0; <span>$j</span> < <span>$wid</span>; ++<span>$j</span><span>){
</span><span>33</span>             <span>$rgb</span> = imagecolorat(<span>$res</span>,<span>$j</span>,<span>$i</span><span>);
</span><span>34</span>             <span>$rgbArray</span>[<span>$i</span>][<span>$j</span>] = imagecolorsforindex(<span>$res</span>, <span>$rgb</span><span>);
</span><span>35</span> <span>        }
</span><span>36</span> <span>    }
</span><span>37</span>     <span>return</span> <span>$rgbArray</span><span>;
</span><span>38</span> }

 

 

二、二值化

因为人眼可以分别出验证码,所以验证码的RGB信息就会有一定的特点,这时候需要我们观察一下,直接打印RGB数组是不好观察的…………,好多数啊

在php实现验证码的识别(初级篇)中,作者的判断依据是

无论验证数字颜色如何变化,该数字的 RGB 值总有一个值小于 125

我们先获取他的灰度,再判断

<span> 1</span> <span>/*</span>
<span> 2</span> <span> *获取灰度信息
</span><span> 3</span>  <span>*/</span>
<span> 4</span> <span>function</span><span> getGray(){
</span><span> 5</span>     <span>$grayArray</span> = <span>array</span><span>();
</span><span> 6</span>     <span>$size</span> = <span>$this</span>-><span>ImageSize;
</span><span> 7</span>     <span>$rgbarray</span> = <span>$this</span>-><span>getRgb();
</span><span> 8</span>     <span>$wid</span> = <span>$size</span>['0'<span>];
</span><span> 9</span>     <span>$hid</span> = <span>$size</span>['1'<span>];
</span><span>10</span>     <span>for</span>(<span>$i</span>=0; <span>$i</span> < <span>$hid</span>; ++<span>$i</span><span>){
</span><span>11</span>         <span>for</span>(<span>$j</span>=0; <span>$j</span> < <span>$wid</span>; ++<span>$j</span><span>){
</span><span>12</span>             <span>$grayArray</span>[<span>$i</span>][<span>$j</span>] = (299*<span>$rgbarray</span>[<span>$i</span>][<span>$j</span>]['red']+587*<span>$rgbarray</span>[<span>$i</span>][<span>$j</span>]['green']+144*<span>$rgbarray</span>[<span>$i</span>][<span>$j</span>]['blue'])/1000<span>;
</span><span>13</span> <span>        }
</span><span>14</span> <span>    }
</span><span>15</span>     <span>return</span> <span>$grayArray</span><span>;
</span><span>16</span> }

 

 

然后我们根据灰度信息,打印图片,注意不是打印灰度信息

<span> 1</span> <span>/*</span><span>根据灰度信息打印图片</span><span>*/</span>
<span> 2</span> <span>function</span><span> printByGray(){
</span><span> 3</span>     <span>$size</span> = <span>$this</span>-><span>ImageSize;    
</span><span> 4</span>     <span>$grayArray</span> = <span>$this</span>-><span>getGray();
</span><span> 5</span>     <span>$wid</span> = <span>$size</span>['0'<span>];
</span><span> 6</span>     <span>$hid</span> = <span>$size</span>['1'<span>];
</span><span> 7</span>     <span>for</span>(<span>$k</span>=0;<span>$k</span><25;<span>$k</span>++<span>){
</span><span> 8</span>         <span>echo</span> <span>$k</span>."\n"<span>;
</span><span> 9</span>         <span>for</span>(<span>$i</span>=0; <span>$i</span> < <span>$hid</span>; ++<span>$i</span><span>){
</span><span>10</span>             <span>for</span>(<span>$j</span>=0; <span>$j</span> < <span>$wid</span>; ++<span>$j</span><span>){
</span><span>11</span>                 <span>if</span>(<span>$grayArray</span>[<span>$i</span>][<span>$j</span>] < <span>$k</span>*10<span>){
</span><span>12</span>                     <span>echo</span> '■'<span>;
</span><span>13</span>                 }<span>else</span><span>{
</span><span>14</span>                     <span>echo</span> '□'<span>;
</span><span>15</span> <span>                }
</span><span>16</span> <span>            }
</span><span>17</span>             <span>echo</span> "|\n"<span>;
</span><span>18</span> <span>        }
</span><span>19</span>         <span>echo</span> "---------------------------------------------------------------------------------------------------------------\n"<span>;
</span><span>20</span> <span>    }
</span><span>21</span>     
<span>22</span> }

 

注意到,从$grayArray[$i][$j]

<span> 1</span> <span>/*</span>
<span> 2</span> <span> *根据自定义的规则,获取二值化二维数组
</span><span> 3</span> <span> *@return  图片高*宽的二值数组(0,1)
</span><span> 4</span>  <span>*/</span>
<span> 5</span> <span>function</span><span> getErzhi(){
</span><span> 6</span>     <span>$erzhiArray</span> = <span>array</span><span>();
</span><span> 7</span>     <span>$size</span> = <span>$this</span>-><span>ImageSize;
</span><span> 8</span>     <span>$grayArray</span> = <span>$this</span>-><span>getGray();
</span><span> 9</span>     <span>$wid</span> = <span>$size</span>['0'<span>];
</span><span>10</span>     <span>$hid</span> = <span>$size</span>['1'<span>];
</span><span>11</span>     <span>for</span>(<span>$i</span>=0; <span>$i</span> < <span>$hid</span>; ++<span>$i</span><span>){
</span><span>12</span>         <span>for</span>(<span>$j</span>=0; <span>$j</span> <<span>$wid</span>; ++<span>$j</span><span>){
</span><span>13</span>             <span>if</span>( <span>$grayArray</span>[<span>$i</span>][<span>$j</span>]    < 90<span> ){
</span><span>14</span>                 <span>$erzhiArray</span>[<span>$i</span>][<span>$j</span>]=1<span>;
</span><span>15</span>             }<span>else</span><span>{
</span><span>16</span>                 <span>$erzhiArray</span>[<span>$i</span>][<span>$j</span>]=0<span>;
</span><span>17</span> <span>            }
</span><span>18</span> <span>        }
</span><span>19</span> <span>    }
</span><span>20</span>     <span>return</span> <span>$erzhiArray</span><span>;
</span><span>21</span> }

 

 

三、去除噪点

但是我们发现有一些小点影响了我们的判断

我们可以注意到这些事干扰噪点,但是如果我们是机器的话,我们如何判断这些点是否是字符呢?

 

所以接下来,我们需要将这些字符去除。

我们判断,如果一个黑点的上下左右的八个点全部是白,我们就认为它是噪点,并予以清除,赋为白

<span> 1</span> <span>/*</span>
<span> 2</span> <span> *二值化图片降噪
</span><span> 3</span> <span> *@param $erzhiArray二值化数组
</span><span> 4</span>  <span>*/</span>
<span> 5</span> <span>function</span> reduceZao(<span>$erzhiArray</span><span>){
</span><span> 6</span>     <span>$data</span> = <span>$erzhiArray</span><span>;
</span><span> 7</span>     <span>$gao</span> = <span>count</span>(<span>$erzhiArray</span><span>);
</span><span> 8</span>     <span>$chang</span> = <span>count</span>(<span>$erzhiArray</span>['0'<span>]);
</span><span> 9</span> 
<span>10</span>     <span>$jiangzaoErzhiArray</span> = <span>array</span><span>();
</span><span>11</span> 
<span>12</span>     <span>for</span>(<span>$i</span>=0;<span>$i</span><<span>$gao</span>;<span>$i</span>++<span>){
</span><span>13</span>         <span>for</span>(<span>$j</span>=0;<span>$j</span><<span>$chang</span>;<span>$j</span>++<span>){
</span><span>14</span>             <span>$num</span> = 0<span>;  
</span><span>15</span>             <span>if</span>(<span>$data</span>[<span>$i</span>][<span>$j</span>] == 1<span>)  
</span><span>16</span> <span>            {
</span><span>17</span>                 <span>//</span><span> 上  </span>
<span>18</span>                 <span>if</span>(<span>isset</span>(<span>$data</span>[<span>$i</span>-1][<span>$j</span><span>])){  
</span><span>19</span>                     <span>$num</span> = <span>$num</span> + <span>$data</span>[<span>$i</span>-1][<span>$j</span><span>];  
</span><span>20</span> <span>                }  
</span><span>21</span>                 <span>//</span><span> 下  </span>
<span>22</span>                 <span>if</span>(<span>isset</span>(<span>$data</span>[<span>$i</span>+1][<span>$j</span><span>])){  
</span><span>23</span>                     <span>$num</span> = <span>$num</span> + <span>$data</span>[<span>$i</span>+1][<span>$j</span><span>];  
</span><span>24</span> <span>                }  
</span><span>25</span>                 <span>//</span><span> 左  </span>
<span>26</span>                 <span>if</span>(<span>isset</span>(<span>$data</span>[<span>$i</span>][<span>$j</span>-1<span>])){  
</span><span>27</span>                     <span>$num</span> = <span>$num</span> + <span>$data</span>[<span>$i</span>][<span>$j</span>-1<span>];  
</span><span>28</span> <span>                }  
</span><span>29</span>                 <span>//</span><span> 右  </span>
<span>30</span>                 <span>if</span>(<span>isset</span>(<span>$data</span>[<span>$i</span>][<span>$j</span>+1<span>])){  
</span><span>31</span>                     <span>$num</span> = <span>$num</span> + <span>$data</span>[<span>$i</span>][<span>$j</span>+1<span>];  
</span><span>32</span> <span>                }  
</span><span>33</span>                 <span>//</span><span> 上左  </span>
<span>34</span>                 <span>if</span>(<span>isset</span>(<span>$data</span>[<span>$i</span>-1][<span>$j</span>-1<span>])){  
</span><span>35</span>                     <span>$num</span> = <span>$num</span> + <span>$data</span>[<span>$i</span>-1][<span>$j</span>-1<span>];  
</span><span>36</span> <span>                }  
</span><span>37</span>                 <span>//</span><span> 上右  </span>
<span>38</span>                 <span>if</span>(<span>isset</span>(<span>$data</span>[<span>$i</span>-1][<span>$j</span>+1<span>])){  
</span><span>39</span>                     <span>$num</span> = <span>$num</span> + <span>$data</span>[<span>$i</span>-1][<span>$j</span>+1<span>];  
</span><span>40</span> <span>                }  
</span><span>41</span>                 <span>//</span><span> 下左  </span>
<span>42</span>                 <span>if</span>(<span>isset</span>(<span>$data</span>[<span>$i</span>+1][<span>$j</span>-1<span>])){  
</span><span>43</span>                     <span>$num</span> = <span>$num</span> + <span>$data</span>[<span>$i</span>+1][<span>$j</span>-1<span>];  
</span><span>44</span> <span>                }  
</span><span>45</span>                 <span>//</span><span> 下右  </span>
<span>46</span>                 <span>if</span>(<span>isset</span>(<span>$data</span>[<span>$i</span>+1][<span>$j</span>+1<span>])){  
</span><span>47</span>                     <span>$num</span> = <span>$num</span> + <span>$data</span>[<span>$i</span>+1][<span>$j</span>+1<span>];  
</span><span>48</span> <span>                }  
</span><span>49</span> <span>            }
</span><span>50</span> 
<span>51</span>                 <span>if</span>(<span>$num</span> < 1<span>){  
</span><span>52</span>                     <span>$jiangzaoErzhiArray</span>[<span>$i</span>][<span>$j</span>] = 0<span>;  
</span><span>53</span>                 }<span>else</span><span>{
</span><span>54</span>                     <span>$jiangzaoErzhiArray</span>[<span>$i</span>][<span>$j</span>] = 1<span>;  
</span><span>55</span> <span>                }
</span><span>56</span> <span>        }
</span><span>57</span> <span>    }
</span><span>58</span>     <span>return</span> <span>$jiangzaoErzhiArray</span><span>;    
</span><span>59</span> 
<span>60</span> }

 

 

我们发现噪点消失了。

 

四、分割

这个时候,我们就需要对单一数字字母进行操作了,我们先将数字提取出来。

有些验证码字符相连,特别难!!!

我们分别从左到右,从右到左,从上到下,从下到上,进行扫描,去除白点,找到边框。

<span> 1</span> <span>/*</span>
<span> 2</span> <span> *归一化处理,针对一个个的数字,即去除字符周围的白点
</span><span> 3</span> <span> *@param $singleArray 二值化数组
</span><span> 4</span>  <span>*/</span>
<span> 5</span> <span>function</span> getJinsuo(<span>$singleArray</span><span>){
</span><span> 6</span>     <span>$dianCount</span> = 0<span>;
</span><span> 7</span>     <span>$rearr</span> = <span>array</span><span>();
</span><span> 8</span>     
<span> 9</span>     <span>$gao</span> = <span>count</span>(<span>$singleArray</span><span>);
</span><span>10</span>     <span>$kuan</span> = <span>count</span>(<span>$singleArray</span>['0'<span>]);
</span><span>11</span>     
<span>12</span>     <span>$dianCount</span> = 0<span>;
</span><span>13</span>     <span>$shangKuang</span> = 0<span>;
</span><span>14</span>     <span>$xiaKuang</span> = 0<span>;
</span><span>15</span>     <span>$zuoKuang</span> = 0<span>;
</span><span>16</span>     <span>$youKuang</span> = 0<span>;
</span><span>17</span>     <span>//</span><span>从上到下扫描</span>
<span>18</span>     <span>for</span>(<span>$i</span>=0; <span>$i</span> < <span>$gao</span>; ++<span>$i</span><span>){
</span><span>19</span>         <span>for</span>(<span>$j</span>=0; <span>$j</span> < <span>$kuan</span>; ++<span>$j</span><span>){
</span><span>20</span>             <span>if</span>( <span>$singleArray</span>[<span>$i</span>][<span>$j</span>] == 1<span>){
</span><span>21</span>                 <span>$dianCount</span>++<span>;
</span><span>22</span> <span>            }
</span><span>23</span> <span>        }
</span><span>24</span>         <span>if</span>(<span>$dianCount</span>>1<span>){
</span><span>25</span>             <span>$shangKuang</span> = <span>$i</span><span>;
</span><span>26</span>             <span>$dianCount</span> = 0<span>;
</span><span>27</span>             <span>break</span><span>;
</span><span>28</span> <span>        }
</span><span>29</span> <span>    }
</span><span>30</span>     <span>//</span><span>从下到上扫描</span>
<span>31</span>     <span>for</span>(<span>$i</span>=<span>$gao</span>-1; <span>$i</span> > -1; <span>$i</span>--<span>){
</span><span>32</span>         <span>for</span>(<span>$j</span>=0; <span>$j</span> < <span>$kuan</span>; ++<span>$j</span><span>){
</span><span>33</span>             <span>if</span>( <span>$singleArray</span>[<span>$i</span>][<span>$j</span>] == 1<span>){
</span><span>34</span>                 <span>$dianCount</span>++<span>;
</span><span>35</span> <span>            }
</span><span>36</span> <span>        }
</span><span>37</span>         <span>if</span>(<span>$dianCount</span>>1<span>){
</span><span>38</span>             <span>$xiaKuang</span> = <span>$i</span><span>;
</span><span>39</span>             <span>$dianCount</span> = 0<span>;
</span><span>40</span>             <span>break</span><span>;
</span><span>41</span> <span>        }
</span><span>42</span> <span>    }
</span><span>43</span>     <span>//</span><span>从左到右扫描</span>
<span>44</span>     <span>for</span>(<span>$i</span>=0; <span>$i</span> < <span>$kuan</span>; ++<span>$i</span><span>){
</span><span>45</span>         <span>for</span>(<span>$j</span>=0; <span>$j</span> < <span>$gao</span>; ++<span>$j</span><span>){
</span><span>46</span>             <span>if</span>( <span>$singleArray</span>[<span>$j</span>][<span>$i</span>] == 1<span>){
</span><span>47</span>                 <span>$dianCount</span>++<span>;
</span><span>48</span> <span>            }
</span><span>49</span> <span>        }
</span><span>50</span>         <span>if</span>(<span>$dianCount</span>>1<span>){
</span><span>51</span>             <span>$zuoKuang</span> = <span>$i</span><span>;
</span><span>52</span>             <span>$dianCount</span> = 0<span>;
</span><span>53</span>             <span>break</span><span>;
</span><span>54</span> <span>        }
</span><span>55</span> <span>    }
</span><span>56</span>     <span>//</span><span>从右到左扫描</span>
<span>57</span>     <span>for</span>(<span>$i</span>=<span>$kuan</span>-1; <span>$i</span> > -1; --<span>$i</span><span>){
</span><span>58</span>         <span>for</span>(<span>$j</span>=0; <span>$j</span> < <span>$gao</span>; ++<span>$j</span><span>){
</span><span>59</span>             <span>if</span>( <span>$singleArray</span>[<span>$j</span>][<span>$i</span>] == 1<span>){
</span><span>60</span>                 <span>$dianCount</span>++<span>;
</span><span>61</span> <span>            }
</span><span>62</span> <span>        }
</span><span>63</span>         <span>if</span>(<span>$dianCount</span>>1<span>){
</span><span>64</span>             <span>$youKuang</span> = <span>$i</span><span>;
</span><span>65</span>             <span>$dianCount</span> = 0<span>;
</span><span>66</span>             <span>break</span><span>;
</span><span>67</span> <span>        }
</span><span>68</span> <span>    }
</span><span>69</span>     <span>for</span>(<span>$i</span>=0;<span>$i</span><<span>$xiaKuang</span>-<span>$shangKuang</span>+1;<span>$i</span>++<span>){
</span><span>70</span>         <span>for</span>(<span>$j</span>=0;<span>$j</span><<span>$youKuang</span>-<span>$zuoKuang</span>+1;<span>$j</span>++<span>){
</span><span>71</span>             <span>$rearr</span>[<span>$i</span>][<span>$j</span>] = <span>$singleArray</span>[<span>$shangKuang</span>+<span>$i</span>][<span>$zuoKuang</span>+<span>$j</span><span>];
</span><span>72</span> <span>        }
</span><span>73</span> <span>    }
</span><span>74</span>     <span>return</span> <span>$rearr</span><span>;
</span><span>75</span> }

 

 

然后从左到右扫描,找到字符的分割

返回三维数组,每一维就是一个字符。

<span> 1</span> <span>/*</span>
<span> 2</span> <span> *切割成三维数组,每个小数字在一个数组里面
</span><span> 3</span> <span> *只适用四个数字一起的数组
</span><span> 4</span> <span> *@param 经过归一化处理的二值化数组
</span><span> 5</span>  <span>*/</span>
<span> 6</span> <span>function</span> cutSmall(<span>$erzhiArray</span><span>){
</span><span> 7</span>     <span>$doubleArray</span> = <span>array</span><span>();
</span><span> 8</span>     <span>$jieZouyou</span> = <span>array</span><span>();
</span><span> 9</span>     
<span>10</span>     <span>$gao</span> = <span>count</span>(<span>$erzhiArray</span><span>);
</span><span>11</span>     <span>$kuan</span> = <span>count</span>(<span>$erzhiArray</span>['0'<span>]);
</span><span>12</span>     
<span>13</span>     <span>$jie</span> = 0<span>;
</span><span>14</span>     <span>$s</span> = 0<span>;
</span><span>15</span>     <span>$jieZouyou</span>[<span>$s</span>] = 0<span>;
</span><span>16</span>     <span>$s</span>++<span>;
</span><span>17</span>     <span>//</span><span>从左到右扫描</span>
<span>18</span>     
<span>19</span>     <span>for</span>(<span>$i</span>=0; <span>$i</span> < <span>$kuan</span><span>;){
</span><span>20</span>         <span>for</span>(<span>$j</span>=0; <span>$j</span> < <span>$gao</span>; ++<span>$j</span><span>){
</span><span>21</span>             <span>$jie</span> = <span>$jie</span> + <span>$erzhiArray</span>[<span>$j</span>][<span>$i</span><span>];
</span><span>22</span> <span>        }
</span><span>23</span>         <span>//</span><span>如果有一列全部是白,设置$jieZouyou,并且跳过中间空白部分</span>
<span>24</span>         <span>if</span>(<span>$jie</span> == 0<span>){
</span><span>25</span>             <span>$jieZouyou</span>[<span>$s</span>] = <span>$i</span>+1<span>;
</span><span>26</span>             <span>do</span><span>{
</span><span>27</span>                 <span>$n</span> = ++<span>$i</span><span>;
</span><span>28</span>                 <span>$qian</span> = 0<span>;
</span><span>29</span>                 <span>$hou</span> = 0<span>;
</span><span>30</span>                 <span>for</span>(<span>$m</span>=0; <span>$m</span> < <span>$gao</span>; ++<span>$m</span><span>){
</span><span>31</span>                     <span>$qian</span> = <span>$qian</span> + <span>$erzhiArray</span>[<span>$m</span>][<span>$n</span><span>];
</span><span>32</span>                     <span>$hou</span> = <span>$hou</span> + <span>$erzhiArray</span>[<span>$m</span>][<span>$n</span>+1<span>];                        
</span><span>33</span> <span>                }
</span><span>34</span>                 <span>$jieZouyou</span>[<span>$s</span>+1] = <span>$n</span>+1<span>;
</span><span>35</span> <span>            }
</span><span>36</span>             <span>//</span><span>当有两列同时全部为白,说明有间隙,循环,知道间隙没有了</span>
<span>37</span>             <span>while</span>(<span>$qian</span> == 0 && <span>$hou</span> == 0<span>);
</span><span>38</span>             <span>$s</span>+=2<span>;
</span><span>39</span>             <span>$i</span>++<span>;
</span><span>40</span>         }<span>else</span><span>{
</span><span>41</span>             <span>$i</span>++<span>;    
</span><span>42</span> <span>        }
</span><span>43</span>         
<span>44</span>         <span>$jie</span> = 0<span>;
</span><span>45</span> <span>    }
</span><span>46</span>     <span>$jieZouyou</span>[] = <span>$kuan</span><span>;
</span><span>47</span>     <span>//</span><span>极端节点数量,(应该是字符个数)*2</span>
<span>48</span>     <span>$jieZouyouCount</span> = <span>count</span>(<span>$jieZouyou</span><span>);
</span><span>49</span>     
<span>50</span>     <span>for</span>(<span>$k</span>=0;<span>$k</span><<span>$jieZouyouCount</span>/2;<span>$k</span>++<span>){
</span><span>51</span>         <span>for</span>(<span>$i</span>=0; <span>$i</span> < <span>$gao</span>; <span>$i</span>++<span>){
</span><span>52</span>             <span>for</span>(<span>$j</span>=0; <span>$j</span> < <span>$jieZouyou</span>[<span>$k</span>*2+1]-<span>$jieZouyou</span>[<span>$k</span>*2]-1; ++<span>$j</span><span>){
</span><span>53</span>                 <span>$doubleArray</span>[<span>$k</span>][<span>$i</span>][<span>$j</span>] = <span>$erzhiArray</span>[<span>$i</span>][<span>$j</span>+<span>$jieZouyou</span>[<span>$k</span>*2<span>]];
</span><span>54</span> <span>            }
</span><span>55</span> <span>        }
</span><span>56</span>         
<span>57</span> <span>    }
</span><span>58</span>     <span>return</span> <span>$doubleArray</span><span>;
</span><span>59</span> }

 

五、倾斜调整

我们发现第三个9有一点倾斜,

我们需要将倾斜的图片“正”过来

人怎么处理的呢,先眼睛观察“倾斜了多少度”,然后把图片扭过来多少度,并且观察->负反馈->大脑传递扭转角度时刻在发生,最后图片就“正”过来了。

人是怎么观察“倾斜”的,以上面的“2”做例子,可能是右上方(左下方)的黑色比左上方(右下方)的多?

我们建立X轴正向向下,Y轴向右的直角坐标系

我们计算每一层的黑点的分布中点坐标,得到一系列离散点,计算这些点所在的直线(线性回归方程的计算,),公式y = b*x+a,

竟然有用到这个公式的一天!!!

大概就是一条倾斜的直线了,通过直线计算直线倾斜角度,然后转这么多的角度,图片应该就“正”了吧。

其中a,b的计算如下

<span> 1</span> <span>/*</span>
<span> 2</span> <span> *定义求线性回归A和B的函数
</span><span> 3</span> <span> *@param $zuobiaoArray坐标的三维数组
</span><span> 4</span>  <span>*/</span>
<span> 5</span> <span>function</span> getHuigui(<span>$zuobiaoArray</span><span>){
</span><span> 6</span>     <span>$y8</span> = 0<span>;
</span><span> 7</span>     <span>$x8</span> = 0<span>;
</span><span> 8</span>     <span>$x2</span> = 0<span>;
</span><span> 9</span>     <span>$xy</span> = 0<span>;
</span><span>10</span>     <span>$geshu</span> = <span>count</span>(<span>$zuobiaoArray</span><span>);
</span><span>11</span>     <span>for</span>(<span>$i</span>=0;<span>$i</span><<span>$geshu</span>;<span>$i</span>++<span>){
</span><span>12</span>         <span>$y8</span> = <span>$y8</span>+<span>$zuobiaoArray</span>[<span>$i</span>]['y'<span>];
</span><span>13</span>         <span>$x8</span> = <span>$x8</span>+<span>$zuobiaoArray</span>[<span>$i</span>]['x'<span>];
</span><span>14</span>         <span>$xy</span> = <span>$xy</span>+<span>$zuobiaoArray</span>[<span>$i</span>]['y']*<span>$zuobiaoArray</span>[<span>$i</span>]['x'<span>];
</span><span>15</span>         <span>$x2</span> = <span>$x2</span> + <span>$zuobiaoArray</span>[<span>$i</span>]['x']*<span>$zuobiaoArray</span>[<span>$i</span>]['x'<span>];;
</span><span>16</span> <span>    }
</span><span>17</span>     <span>$y8</span> = <span>$y8</span>/<span>$geshu</span><span>;
</span><span>18</span>     <span>$x8</span> = <span>$x8</span>/<span>$geshu</span><span>;
</span><span>19</span>     
<span>20</span>     <span>$b</span> = (<span>$xy</span>-<span>$geshu</span>*<span>$y8</span>*<span>$x8</span>)/(<span>$x2</span>-<span>$geshu</span>*<span>$x8</span>*<span>$x8</span><span>);
</span><span>21</span>     <span>$a</span> = <span>$y8</span>-<span>$b</span>*<span>$x8</span><span>;
</span><span>22</span>     <span>$re</span>['a'] = <span>$a</span><span>;
</span><span>23</span>     <span>$re</span>['b'] = <span>$b</span><span>;
</span><span>24</span>     <span>return</span> <span>$re</span><span>;
</span><span>25</span>     <span>//</span><span>y = b * x + a</span>
<span>26</span> }

 

怎么转角?

1、可以直接对图片进行操作,但是发现有比较大的失真,就没有继续了。
2、或者,对黑点白点的坐标进行操作&hellip;&hellip;

这就是三角函数了,好长时间不碰三角函数,都差点忘记了。

定义函数

<span> 1</span> <span>/*</span>
<span> 2</span> <span> *定义转化坐标的函数
</span><span> 3</span> <span> *@param $x x坐标即$i
</span><span> 4</span> <span> *@param $y y坐标,即j
</span><span> 5</span> <span> *@param $b 线性回归方程的b参数 
</span><span> 6</span>  <span>*/</span> 
<span> 7</span> <span>function</span> getNewZuobiao(<span>$x</span>,<span>$y</span>,<span>$b</span><span>){
</span><span> 8</span>     <span>if</span>(<span>$x</span> == 0<span>){
</span><span> 9</span>         <span>if</span>(<span>$y</span>>0<span>){
</span><span>10</span>             <span>$xianJiao</span> = M_PI/2<span>;
</span><span>11</span>         }<span>elseif</span>(<span>$y</span><0<span>){
</span><span>12</span>             <span>$xianJiao</span> = -M_PI/2<span>;
</span><span>13</span>         }<span>else</span><span>{
</span><span>14</span>             <span>$p</span>['x'] = 0<span>;
</span><span>15</span>             <span>$p</span>['y'] = 0<span>;
</span><span>16</span>             <span>return</span> <span>$p</span><span>;
</span><span>17</span> <span>        }
</span><span>18</span>     }<span>else</span><span>{
</span><span>19</span>         <span>$xianJiao</span> = <span>atan</span>(<span>$y</span>/<span>$x</span><span>);    
</span><span>20</span> <span>    }
</span><span>21</span>     <span>$jiao</span> =<span>$xianJiao</span>-<span>atan</span>(<span>$b</span><span>);
</span><span>22</span>     <span>$chang</span> = <span>sqrt</span>(<span>$x</span>*<span>$x</span>+<span>$y</span>*<span>$y</span><span>);
</span><span>23</span>     <span>$p</span>['x'] = <span>$chang</span>*<span>cos</span>(<span>$jiao</span><span>);
</span><span>24</span>     <span>$p</span>['y'] = <span>$chang</span>*<span>sin</span>(<span>$jiao</span><span>);
</span><span>25</span>     <span>return</span> <span>$p</span><span>;
</span><span>26</span> }

 

转角吧

 

<span> 1</span> <span>/*</span>
<span> 2</span> <span> *对【单个】数字的二值化二维数组进行倾斜调整
</span><span> 3</span> <span> *@param  $singleArray  高*宽的二值数组(0,1)
</span><span> 4</span>  <span>*/</span>
<span> 5</span> <span>function</span> singleSlopeAdjust(<span>$singleErzhiArray</span><span>){
</span><span> 6</span>     <span>$slopeArray</span> = <span>array</span><span>();
</span><span> 7</span>     <span>$gao</span> = <span>count</span>(<span>$singleErzhiArray</span><span>);
</span><span> 8</span>     <span>$chang</span> = <span>count</span>(<span>$singleErzhiArray</span>['0'<span>]);
</span><span> 9</span>     
<span>10</span>     <span>//</span><span>初始化$slopeArray</span>
<span>11</span>     <span>for</span>(<span>$i</span>=0;<span>$i</span><<span>$gao</span>*4;<span>$i</span>++<span>){
</span><span>12</span>         <span>for</span>(<span>$j</span>=0;<span>$j</span><<span>$chang</span>*4;<span>$j</span>++<span>){
</span><span>13</span>             <span>$slopeArray</span>[<span>$i</span>][<span>$j</span>] = 0<span>;
</span><span>14</span> <span>        }
</span><span>15</span> <span>    }
</span><span>16</span>     
<span>17</span>     <span>//</span><span>初始化中心坐标(是数组的下标)</span>
<span>18</span>     <span>$centerXfoalt</span> = (<span>$gao</span>-1)/2<span>;
</span><span>19</span>     <span>$centerYfoalt</span> = (<span>$chang</span>-1)/2<span>;
</span><span>20</span>     <span>$centerX</span> = <span>ceil</span>(<span>$centerXfoalt</span><span>);
</span><span>21</span>     <span>$centerY</span> = <span>ceil</span>(<span>$centerYfoalt</span><span>);
</span><span>22</span>     
<span>23</span>     <span>//</span><span>初始化图片倾斜诶角度</span>
<span>24</span>     <span>/*</span><span>斜率的计算!!!!!,回归方程</span><span>*/</span>
<span>25</span>     <span>//</span><span>从上到下扫描,计算中点,求得一串坐标($i,$ava)</span>
<span>26</span>     <span>for</span>(<span>$i</span>=0;<span>$i</span><<span>$gao</span>;<span>$i</span>++<span>){
</span><span>27</span>         <span>$Num</span> = 0<span>;
</span><span>28</span>         <span>$Amount</span> = 0<span>;
</span><span>29</span>         <span>for</span>(<span>$j</span>=0;<span>$j</span><<span>$chang</span>;<span>$j</span>++<span>){
</span><span>30</span>             <span>if</span>(<span>$singleErzhiArray</span>[<span>$i</span>][<span>$j</span>] == 1<span>){
</span><span>31</span>                 <span>$Num</span> = <span>$Num</span>+<span>$j</span><span>;
</span><span>32</span>                 <span>$Amount</span>++<span>;
</span><span>33</span> <span>            }
</span><span>34</span> <span>        }
</span><span>35</span>         <span>if</span>(<span>$Amount</span> == 0<span>){
</span><span>36</span>             <span>$Ava</span>[<span>$i</span>] = <span>$chang</span>/2<span>;    
</span><span>37</span>         }<span>else</span><span>{
</span><span>38</span>             <span>$Ava</span>[<span>$i</span>] = <span>$Num</span>/<span>$Amount</span><span>;
</span><span>39</span> <span>        }
</span><span>40</span> <span>    }
</span><span>41</span> 
<span>42</span>     
<span>43</span>     <span>//</span><span>计算线性回归方程的b与a</span>
<span>44</span>     <span>$zuo</span> = <span>array</span><span>();
</span><span>45</span>     <span>for</span>(<span>$j</span>=0;<span>$j</span><<span>count</span>(<span>$Ava</span>);<span>$j</span>++<span>){
</span><span>46</span>         <span>$zuo</span>[<span>$j</span>]['x'] = <span>$j</span><span>;
</span><span>47</span>         <span>$zuo</span>[<span>$j</span>]['y'] = <span>$Ava</span>[<span>$j</span><span>];
</span><span>48</span> <span>    }
</span><span>49</span>     <span>$res</span> = <span>$this</span>->getHuigui(<span>$zuo</span><span>);
</span><span>50</span>     <span>$zuoB</span> = <span>$res</span>['b'<span>];
</span><span>51</span> 
<span>52</span>     
<span>53</span>     <span>for</span>(<span>$i</span>=0;<span>$i</span><<span>$gao</span>;<span>$i</span>++<span>){
</span><span>54</span>         <span>for</span>(<span>$j</span>=0;<span>$j</span><<span>$chang</span>;<span>$j</span>++<span>){
</span><span>55</span>             <span>if</span>(<span>$singleErzhiArray</span>[<span>$i</span>][<span>$j</span>] == 1<span>){
</span><span>56</span>                 <span>$splodeZuobiao</span> = <span>$this</span>->getNewZuobiao(<span>$i</span>,<span>$j</span>,<span>$zuoB</span><span>);
</span><span>57</span>                 <span>$splodeX</span> = <span>$splodeZuobiao</span>['x'<span>];
</span><span>58</span>                 <span>$splodeY</span> = <span>$splodeZuobiao</span>['y'<span>];
</span><span>59</span>                 <span>$slopeArray</span>[<span>$splodeX</span>+<span>$gao</span>][<span>$splodeY</span>+<span>$chang</span>] = 1<span>;
</span><span>60</span> <span>            }
</span><span>61</span> <span>        }
</span><span>62</span> <span>    }
</span><span>63</span>     
<span>64</span>     <span>//</span><span>将预处理的数组空白清理</span>
<span>65</span>     <span>$slopeArray</span> = <span>$this</span>->getJinsuo(<span>$slopeArray</span><span>);
</span><span>66</span>     <span>return</span> <span>$slopeArray</span><span>;
</span><span>67</span> }

看到正了一些

 

六、统一大小

上文中因为各种操作,每个字符大小不一,我们需要统一大小

 

七、特征值的建立

有很多方法

1、逐像素特征提取法
这是一种最简单的特征提取方法。它可以对图像进行逐行逐列的扫描,当遇到黑色像素时取其特征值为1,遇到白色像素时取其特征值为0,这样当扫描结束后就获得一个维数与图像中的像素点的个数相同的特征向量矩阵。
这种方法提取的信息量最大,但是它的缺点也很明显,就是适应性不强。

2、骨架特征提取法
两幅图像由于它们的线条的粗细不同,使得两幅图像差别很大,但是将它们的线条进行细化后,统一到相同的宽度,如一个像素宽时,这是两幅图像的差距就不那么明显。利用图形的骨架作为特征来进行数码识别,就使得识别有了一定的适应性。一般使用细化的方法来提取骨架,细化的算法有很多,如Hilditch算法、Rosenfeld算法等。对经过细化的图像利用EveryPixel函数进行处理就可以得到细化后图像的特征向量矩阵。骨架特征提取的方法对于线条粗细不同的数码有一定的适应性,但是图像一旦出现偏移就难以识别。

3、微结构法
微结构法将图像分为几个小块,统计每个小块的像素分布。本文提取出汉字的39个特征,存储在数组f[0]~f[38]中。具体算法可分为四步:

 步骤一:把字符平均分成9份,如图4.1所示,给每一份编号如图4.2,统计每一份内黑色像素的个数,存储在数字tz[0]~tz[9]中,统计在行方向和列方向上每一份内的黑色像素个数和与之相邻的一份内黑色像素个数的比值作为一个特征,例如:行方向上提取特征f[0]=tz[1]/ tz[0],f[1]=tz[2]/ tz[1],f[2]=tz[0]/ tz[2],…,f[8]=tz[6]/ tz[8];列方向上f[9]=tz[3]/ tz[0],f[10]=tz[6]/ tz[3],f[11]=tz[0]/ tz[6],…,f[17]=tz[2]/ tz[8],共18个特征。

步骤二:把字符横向分成三份,如图4.3所示,统计每一份内的黑色像素个数,每一份内的黑色像素个数与前一份内黑色像素个数的比值作为一个特征,f[18]=tz[10]/ tz[9],f[19]=tz[11]/ tz[10],f[20]=tz[9]/ tz[11];把字符纵向分成三份,如图4.4所示,统计每一份内的黑色像素个数,每一份内的黑色像素个数与前一份内黑色像素个数的比值作为一个特征,f[21]=tz[13]/ tz[12],f[22]=tz[14]/ tz[13],f[23]=tz[12]/ tz[14];共六个特征。

步骤三:如图4.5,在竖直方向上找出三列,统计在该列中跳变点的个数,即相邻点像素值从0变到255的次数,共三个特征,记为f[24],f[25],f[26];在水平方向上找出三行列,统计在该行中跳变点的个数,即相邻点象素值从0变到255的次数,共三个特征,记为f[27],f[28],f[29]。

图4.5

步骤四:把每一份内黑色象素的个数tz[0]~tz[9],作为9个特征,记为:f[30]~f[38]。

这样得到汉字的共39个特征,根据这些特征就可以区分每个车牌汉字,进行识别。

 

 

我们使用最简单的逐像素特征提取法。

多多增加数据库,识别率会增加的

 

八、识别验证码

对于一个新的验证码,进行上文操作,然后对比数据库就可以了

<span> 1</span> <span>/*</span>
<span> 2</span> <span> *进行匹配
</span><span> 3</span> <span> *@param  $Image  图片路径
</span><span> 4</span>  <span>*/</span>
<span> 5</span> <span>public</span> <span>function</span> run(<span>$Image</span><span>){
</span><span> 6</span>     <span>$data</span> = <span>array</span>('','','',''<span>);
</span><span> 7</span>     <span>$result</span>=""<span>;
</span><span> 8</span>     <span>$bilu</span> = ''<span>;
</span><span> 9</span>     <span>$maxarr</span> = ''<span>;
</span><span>10</span>     
<span>11</span>     <span>//</span><span>提取特征</span>
<span>12</span>     <span>$this</span>->prepare(<span>$Image</span><span>);
</span><span>13</span>     <span>$yuanshi</span> = <span>$this</span>-><span>getErzhi();
</span><span>14</span>     <span>$yijijiangzao</span> = <span>$this</span>->reduceZao(<span>$yuanshi</span><span>);
</span><span>15</span>     <span>$small</span> = <span>$this</span>->cutSmall(<span>$yijijiangzao</span><span>);
</span><span>16</span>     <span>for</span>(<span>$k</span>=0;<span>$k</span><4;<span>$k</span>++<span>){
</span><span>17</span>         <span>$tianchong</span> = <span>$this</span>->tianChong(<span>$small</span>[<span>$k</span><span>]);
</span><span>18</span>         <span>$tiaozhenjiaodu</span> = <span>$this</span>->singleSlopeAdjust(<span>$tianchong</span><span>);
</span><span>19</span>         <span>$tongyidaxiao</span> = <span>$this</span>->tongyiDaxiao(<span>$tiaozhenjiaodu</span><span>);
</span><span>20</span>         <span>for</span>(<span>$i</span>=0;<span>$i</span><20;<span>$i</span>++<span>){
</span><span>21</span>             <span>for</span>(<span>$j</span>=0;<span>$j</span><20;<span>$j</span>++<span>){
</span><span>22</span>                 <span>$data</span>[<span>$k</span>] .= <span>$tongyidaxiao</span>[<span>$i</span>][<span>$j</span><span>];    
</span><span>23</span> <span>            }    
</span><span>24</span> <span>        }
</span><span>25</span> <span>    }
</span><span>26</span> 
<span>27</span>     <span>//</span><span> 进行关键字匹配</span>
<span>28</span>     <span>foreach</span>(<span>$data</span> <span>as</span> <span>$numKey</span> => <span>$numString</span><span>)
</span><span>29</span> <span>    {
</span><span>30</span> 
<span>31</span>         <span>$max</span> = 0<span>;
</span><span>32</span>         <span>$num</span> = 0<span>;
</span><span>33</span>         <span>foreach</span>(<span>$this</span>->Keys <span>as</span> <span>$value</span> => <span>$key</span><span>)
</span><span>34</span> <span>        {
</span><span>35</span>             <span>similar_text</span>(<span>$value</span>, <span>$numString</span>,<span>$percent</span><span>);
</span><span>36</span>             <span>if</span>(<span>$percent</span> > <span>$max</span><span>)
</span><span>37</span> <span>            {
</span><span>38</span>                 <span>$max</span> = <span>$percent</span><span>;
</span><span>39</span>                 <span>$num</span> = <span>$key</span><span>;
</span><span>40</span>                 <span>$zim</span> = <span>$value</span><span>;
</span><span>41</span> <span>            }
</span><span>42</span>             <span>if</span>(<span>$max</span>>95<span>){
</span><span>43</span>                 <span>break</span><span>;
</span><span>44</span> <span>            }
</span><span>45</span> <span>        }
</span><span>46</span>         <span>$result</span> .=<span>$num</span><span>;
</span><span>47</span>         <span>$maxarr</span>[] = <span>$max</span><span>;
</span><span>48</span> <span>    }
</span><span>49</span>     <span>//</span><span> 查找最佳匹配数字</span>
<span>50</span>     <span>$re</span> = <span>$maxarr</span><span>;
</span><span>51</span>     <span>$re</span>[] = <span>$result</span><span>;
</span><span>52</span>     <span>return</span> <span>$re</span><span>;
</span><span>53</span>     <span>//</span><span>return $result.'|max|一:'.$maxarr['0'].'|二:'.$maxarr['1'].'|三:'.$maxarr['2'].'|四:'.$maxarr['3'];</span>
<span>54</span> }

 

试试:

 

PHP图形验证码识别

Header("Content-type: image/gif");
/*
* 初始化
*/
$border = 0; //是否要边框 1要:0不要
$how = 4; //验证码位数
$w = $how*15; //图片宽度
$h = 20; //图片高度
$fontsize = 5; //字体大小
$alpha = "abcdefghijkmnopqrstuvwxyz"; //验证码内容1:字母
$number = "023456789"; //验证码内容2:数字
$randcode = ""; //验证码字符串初始化
srand((double)microtime()*1000000); //初始化随机数种子

$im = ImageCreate($w, $h); //创建验证图片

/*
* 绘制基本框架
*/
$bgcolor = ImageColorAllocate($im, 255, 255, 255); //设置背景颜色
ImageFill($im, 0, 0, $bgcolor); //填充背景色
if($border)
{
$black = ImageColorAllocate($im, 0, 0, 0); //设置边框颜色
ImageRectangle($im, 0, 0, $w-1, $h-1, $black);//绘制边框
}

/*
* 逐位产生随机字符
*/
for($i=0; $i{
$alpha_or_number = mt_rand(0, 1); //字母还是数字
$str = $alpha_or_number ? $alpha : $number;
$which = mt_rand(0, strlen($str)-1); //取哪个字符
$code = substr($str, $which, 1); //取字符
$j = !$i ? 4 : $j+15; //绘字符位置
$color3 = ImageColorAllocate($im, mt_rand(0,100), mt_rand(0,100), mt_rand(0,100)); //字符随即颜色
ImageChar($im, $fontsize, $j, 3, $code, $color3); //绘字符
$randcode .= $code; //逐位加入验证码字符串
}

/*
* 添加干扰
*/
for($i=0; $i{
$color1 = ImageColorAllocate($im, mt_rand(0,255), mt_rand(0,255), mt_rand(0,255)); //干扰线颜色
ImageArc($im, mt_ra......余下全文>>
 

PHP 验证码识别 或者ASP程序也行怎写程序识别

原理不难,只需通过PHP来生成一张图片!在这张图片上通过PHP的图片处理函数在图片上写几个字符就Ok啦!在写字符时注意将写的字符记录下,这个记录是通过session来做!然后在验证时直接调用$_SESSION变量就可以了!

具体的代码如下:
有两个文件
yangzhengma.php用来显示图片和验证输入的验证码

session_start();
if(!empty($_GET['sub'])){
if($_SESSION['checks'] == $_GET['ma']){
echo "验证码正确
";
}else{
echo "验证码不正确!
";
}
}
?>


<br> 验证码实例<br> <br> <meta http-equiv="content-type" content="text/html;charset=utf-8"> <br><br>
PHP之验证码识别,php验证码_PHP教程



请输入验证码:





注意图片的地址写到PHP生成图片的文件地址

check.php用来生成图片

session_start();
header('content-type:image/jpeg');
$image_width=70;
$image_height=25;
$str="";
$arr=array(1,2,3,4,5,6,7,8,9,'A','B','C','D','E','F','G','H','I','J','K','L','M','N','P','Q','R','S','T','U','V','W','X','Y','Z');
for ($i =0 ; $i ......余下全文>>
 

www.bkjia.comtruehttp://www.bkjia.com/PHPjc/857272.htmlTechArticlePHP之验证码识别,php验证码 首先推荐几篇有关验证码识别的文章,觉得不错 php实现验证码的识别(初级篇) 关于bp神经网格识别验证码 一、思...
声明
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系admin@php.cn
PHP和Python:解释了不同的范例PHP和Python:解释了不同的范例Apr 18, 2025 am 12:26 AM

PHP主要是过程式编程,但也支持面向对象编程(OOP);Python支持多种范式,包括OOP、函数式和过程式编程。PHP适合web开发,Python适用于多种应用,如数据分析和机器学习。

PHP和Python:深入了解他们的历史PHP和Python:深入了解他们的历史Apr 18, 2025 am 12:25 AM

PHP起源于1994年,由RasmusLerdorf开发,最初用于跟踪网站访问者,逐渐演变为服务器端脚本语言,广泛应用于网页开发。Python由GuidovanRossum于1980年代末开发,1991年首次发布,强调代码可读性和简洁性,适用于科学计算、数据分析等领域。

在PHP和Python之间进行选择:指南在PHP和Python之间进行选择:指南Apr 18, 2025 am 12:24 AM

PHP适合网页开发和快速原型开发,Python适用于数据科学和机器学习。1.PHP用于动态网页开发,语法简单,适合快速开发。2.Python语法简洁,适用于多领域,库生态系统强大。

PHP和框架:现代化语言PHP和框架:现代化语言Apr 18, 2025 am 12:14 AM

PHP在现代化进程中仍然重要,因为它支持大量网站和应用,并通过框架适应开发需求。1.PHP7提升了性能并引入了新功能。2.现代框架如Laravel、Symfony和CodeIgniter简化开发,提高代码质量。3.性能优化和最佳实践进一步提升应用效率。

PHP的影响:网络开发及以后PHP的影响:网络开发及以后Apr 18, 2025 am 12:10 AM

PHPhassignificantlyimpactedwebdevelopmentandextendsbeyondit.1)ItpowersmajorplatformslikeWordPressandexcelsindatabaseinteractions.2)PHP'sadaptabilityallowsittoscaleforlargeapplicationsusingframeworkslikeLaravel.3)Beyondweb,PHPisusedincommand-linescrip

PHP类型提示如何起作用,包括标量类型,返回类型,联合类型和无效类型?PHP类型提示如何起作用,包括标量类型,返回类型,联合类型和无效类型?Apr 17, 2025 am 12:25 AM

PHP类型提示提升代码质量和可读性。1)标量类型提示:自PHP7.0起,允许在函数参数中指定基本数据类型,如int、float等。2)返回类型提示:确保函数返回值类型的一致性。3)联合类型提示:自PHP8.0起,允许在函数参数或返回值中指定多个类型。4)可空类型提示:允许包含null值,处理可能返回空值的函数。

PHP如何处理对象克隆(克隆关键字)和__clone魔法方法?PHP如何处理对象克隆(克隆关键字)和__clone魔法方法?Apr 17, 2025 am 12:24 AM

PHP中使用clone关键字创建对象副本,并通过\_\_clone魔法方法定制克隆行为。1.使用clone关键字进行浅拷贝,克隆对象的属性但不克隆对象属性内的对象。2.通过\_\_clone方法可以深拷贝嵌套对象,避免浅拷贝问题。3.注意避免克隆中的循环引用和性能问题,优化克隆操作以提高效率。

PHP与Python:用例和应用程序PHP与Python:用例和应用程序Apr 17, 2025 am 12:23 AM

PHP适用于Web开发和内容管理系统,Python适合数据科学、机器学习和自动化脚本。1.PHP在构建快速、可扩展的网站和应用程序方面表现出色,常用于WordPress等CMS。2.Python在数据科学和机器学习领域表现卓越,拥有丰富的库如NumPy和TensorFlow。

See all articles

热AI工具

Undresser.AI Undress

Undresser.AI Undress

人工智能驱动的应用程序,用于创建逼真的裸体照片

AI Clothes Remover

AI Clothes Remover

用于从照片中去除衣服的在线人工智能工具。

Undress AI Tool

Undress AI Tool

免费脱衣服图片

Clothoff.io

Clothoff.io

AI脱衣机

AI Hentai Generator

AI Hentai Generator

免费生成ai无尽的。

热门文章

R.E.P.O.能量晶体解释及其做什么(黄色晶体)
1 个月前By尊渡假赌尊渡假赌尊渡假赌
R.E.P.O.最佳图形设置
1 个月前By尊渡假赌尊渡假赌尊渡假赌
威尔R.E.P.O.有交叉游戏吗?
1 个月前By尊渡假赌尊渡假赌尊渡假赌

热工具

MinGW - 适用于 Windows 的极简 GNU

MinGW - 适用于 Windows 的极简 GNU

这个项目正在迁移到osdn.net/projects/mingw的过程中,你可以继续在那里关注我们。MinGW:GNU编译器集合(GCC)的本地Windows移植版本,可自由分发的导入库和用于构建本地Windows应用程序的头文件;包括对MSVC运行时的扩展,以支持C99功能。MinGW的所有软件都可以在64位Windows平台上运行。

Dreamweaver CS6

Dreamweaver CS6

视觉化网页开发工具

WebStorm Mac版

WebStorm Mac版

好用的JavaScript开发工具

ZendStudio 13.5.1 Mac

ZendStudio 13.5.1 Mac

功能强大的PHP集成开发环境

记事本++7.3.1

记事本++7.3.1

好用且免费的代码编辑器