@@ -6,3 +6,4 @@
|
||||
Prj-Linux/lpr/TEST_*
|
||||
Prj-Linux/*build*/
|
||||
*.pyc
|
||||
/Prj-PHP/build
|
||||
|
||||
+4
-13
@@ -1,21 +1,12 @@
|
||||
cmake_minimum_required(VERSION 3.6)
|
||||
project(platescan)
|
||||
|
||||
set(OpenCV_DIR /usr/platescan/opencv-3.3.0/release/)
|
||||
#set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -g -O2 -std=c++11 -fpic -o")
|
||||
#set(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR})
|
||||
|
||||
set(CMAKE_CXX_STANDARD 11)
|
||||
|
||||
set(PHP_CONFIG_DIR /etc/php.d/)
|
||||
set(PHP_CONFIG php-config)
|
||||
set(POST_COMPILE_COMMAND systemctl restart php-fpm)
|
||||
|
||||
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++11")
|
||||
set(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR})
|
||||
find_package(OpenCV 3.3.0 REQUIRED)
|
||||
include_directories( ${OpenCV_INCLUDE_DIRS})
|
||||
include_directories(include)
|
||||
|
||||
|
||||
add_library( # Sets the name of the library.
|
||||
platescan
|
||||
|
||||
@@ -42,10 +33,10 @@ target_link_libraries(
|
||||
${OpenCV_LIBS}
|
||||
)
|
||||
|
||||
execute_process(COMMAND ${PHP_CONFIG} --extension-dir
|
||||
execute_process(COMMAND php-config --extension-dir
|
||||
OUTPUT_VARIABLE LIBRARY_DIR)
|
||||
|
||||
message("Test ${LIBRARY_DIR} failed.")
|
||||
message("PHP_EXTENSIONS_DIR ${LIBRARY_DIR}")
|
||||
|
||||
add_custom_command(TARGET platescan
|
||||
POST_BUILD
|
||||
|
||||
+37
-3
@@ -1,9 +1,29 @@
|
||||
|
||||
# Prj-PHP
|
||||
|
||||
HyperLPR 在PHP扩展程序中的实现,核心代码拷贝了 Prj-Linux 中庾金科大牛的代码。我做的这部分工作主要是配置编译成PHP扩展程序。
|
||||
|
||||
## CPP 依赖
|
||||
|
||||
+ Opencv 3.3
|
||||
+ PHPCPP
|
||||
|
||||
## Linux/Mac 编译
|
||||
|
||||
```bash
|
||||
mkdir build
|
||||
cd build
|
||||
cmake ../
|
||||
make -j
|
||||
```
|
||||
|
||||
## DEMO
|
||||
|
||||
```php
|
||||
$path = realpath("demo.png");
|
||||
$res = platescan($path);
|
||||
// 也可编译完后直接在tests目录直接运行 php platescan.php
|
||||
$path = realpath("demo.png"); // 图片文件所在路径,realpath转为绝对路径
|
||||
$model = realpath("model"); // 模型资源所在文件夹
|
||||
$res = platescan($path, $model, 0.8);
|
||||
var_dump($res); // string(9) "苏ED0N19"
|
||||
|
||||
```
|
||||
@@ -12,5 +32,19 @@ var_dump($res); // string(9) "苏ED0N19"
|
||||
|
||||

|
||||
|
||||
## 测试备忘
|
||||
|
||||
#### 感谢各位大牛!
|
||||
经多次测试发现部分图片难以识别或者容易识别错误,经过筛选反推出如下规律:
|
||||
|
||||
### 识别精度高的图片
|
||||
|
||||
+ 图片中包含有整个车身
|
||||
+ 图片清晰度较高,不模糊
|
||||
+ 图片拍摄角度为正面拍摄,车牌在图片中没有较大幅度的倾斜
|
||||
+ 图片中的车牌在整个图片中所占位置较小
|
||||
|
||||
### 识别精度低的图片
|
||||
|
||||
+ 图片模糊,程序未能裁切出正确的车牌,或者裁切后因图片太模糊而无法识别(此处应该可以通过训练更多样本解决)
|
||||
+ 图片中的车牌在整个图片中占了1/3的位置甚至更高
|
||||
+ 图片拍摄角度为俯角拍摄,车牌在图片中是倾斜着的
|
||||
|
||||
+56
-70
@@ -1,5 +1,6 @@
|
||||
//
|
||||
// Created by Coleflowers on 20/06/2018.
|
||||
// Updated by Justid on 02/07/2018.
|
||||
//
|
||||
#include <phpcpp.h>
|
||||
#include <iostream>
|
||||
@@ -10,88 +11,69 @@
|
||||
#include "PlateDetection.h"
|
||||
#include "FastDeskew.h"
|
||||
#include "FineMapping.h"
|
||||
#include "Pipeline.h"
|
||||
|
||||
|
||||
std::vector<std::string> chars{"京","沪","津","渝","冀","晋","蒙","辽","吉","黑","苏","浙","皖","闽","赣","鲁","豫","鄂","湘","粤","桂","琼","川","贵","云","藏","陕","甘","青","宁","新","0","1","2","3","4","5","6","7","8","9","A","B","C","D","E","F","G","H","J","K","L","M","N","P","Q","R","S","T","U","V","W","X","Y","Z"};
|
||||
/* 关闭原opencv报错输出 */
|
||||
int handleError( int status, const char* func_name,
|
||||
const char* err_msg, const char* file_name,
|
||||
int line, void* userdata )
|
||||
{
|
||||
//Do nothing -- will suppress console output
|
||||
return 0; //Return value is not used
|
||||
}
|
||||
|
||||
/**
|
||||
* 车牌图片识别
|
||||
* @param imgpath 图片的绝对路径
|
||||
* @params imgpath 图片的绝对路径
|
||||
* @params modelpath 识别模型所在文件夹路径
|
||||
* @params confidence 可信度要求,可选参数,默认值0.75
|
||||
* @return 车牌号 图片路径的图片不存在的话 返回空值
|
||||
*/
|
||||
cv::String scan(const char *imgpath){
|
||||
// 读取图片获取车牌的粗略部分
|
||||
cv::Mat image = cv::imread(imgpath);
|
||||
if(!image.data) {
|
||||
printf("No img data!\n");
|
||||
return "";
|
||||
cv::String scan(std::string imgpath, std::string modelpath, double confidence){
|
||||
cv::redirectError(handleError);
|
||||
try {
|
||||
pr::PipelinePR prc(modelpath+"/cascade.xml",
|
||||
modelpath+"/HorizonalFinemapping.prototxt",modelpath+"/HorizonalFinemapping.caffemodel",
|
||||
modelpath+"/Segmentation.prototxt",modelpath+"/Segmentation.caffemodel",
|
||||
modelpath+"/CharacterRecognization.prototxt",modelpath+"/CharacterRecognization.caffemodel",
|
||||
modelpath+"/SegmentationFree.prototxt",modelpath+"/SegmentationFree.caffemodel"
|
||||
);
|
||||
cv::Mat image = cv::imread(imgpath);
|
||||
std::vector<pr::PlateInfo> res = prc.RunPiplineAsImage(image,pr::SEGMENTATION_FREE_METHOD);
|
||||
|
||||
cv::String platenum = "";
|
||||
for(auto st:res) {
|
||||
if(st.confidence>confidence) {
|
||||
platenum = st.getPlateName();
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return platenum;
|
||||
}
|
||||
pr::PlateDetection plateDetection("/usr/platescan/src/lpr/model/cascade.xml");
|
||||
std::vector<pr::PlateInfo> plates;
|
||||
plateDetection.plateDetectionRough(image,plates);
|
||||
// todo 处理发现的每一个车牌信息
|
||||
// 目前只处理了一组
|
||||
cv::Mat img;
|
||||
for(pr::PlateInfo platex:plates) {
|
||||
// 暂时不保存了
|
||||
//cv::imwrite("res/mmm.png",platex.getPlateImage());
|
||||
img = platex.getPlateImage();
|
||||
catch( cv::Exception& e )
|
||||
{
|
||||
const char* err_msg = e.what();
|
||||
throw Php::Exception(err_msg);
|
||||
}
|
||||
|
||||
// 车牌部分
|
||||
cv::Mat image_finemapping = pr::FineMapping::FineMappingVertical(img);
|
||||
pr::FineMapping finemapper = pr::FineMapping("/usr/platescan/src/lpr/model/HorizonalFinemapping.prototxt","/usr/platescan/src/lpr/model/HorizonalFinemapping.caffemodel");
|
||||
|
||||
//
|
||||
image_finemapping = pr::fastdeskew(image_finemapping, 5);
|
||||
|
||||
// image_finemapping = finemapper.FineMappingHorizon(image_finemapping,0,-3);
|
||||
// Android 代码里这个是
|
||||
// 改了之后部分图片数据精度发生变化 ,比如 字母精度有了,但是汉字又错了
|
||||
image_finemapping = finemapper.FineMappingHorizon(image_finemapping,2,5);
|
||||
// 暂时不保存了
|
||||
//cv::imwrite("res/m222222222.png",image_finemapping);
|
||||
|
||||
// 设置尺寸 识别
|
||||
cv::Mat demo = image_finemapping;
|
||||
cv::resize(demo,demo,cv::Size(136,36));
|
||||
//cv::imwrite("res/m333333.png",demo);
|
||||
|
||||
cv::Mat respones;
|
||||
pr::PlateSegmentation plateSegmentation("/usr/platescan/src/lpr/model/Segmentation.prototxt","/usr/platescan/src/lpr/model/Segmentation.caffemodel");
|
||||
pr::PlateInfo plate;
|
||||
plate.setPlateImage(demo);
|
||||
std::vector<cv::Rect> rects;
|
||||
plateSegmentation.segmentPlatePipline(plate,1,rects);
|
||||
plateSegmentation.ExtractRegions(plate,rects);
|
||||
|
||||
pr::GeneralRecognizer *recognizer = new pr::CNNRecognizer("/usr/platescan/src/lpr/model/CharacterRecognization.prototxt","/usr/platescan/src/lpr/model/CharacterRecognization.caffemodel");
|
||||
recognizer->SegmentBasedSequenceRecognition(plate);
|
||||
//std::cout<<plate.decodePlateNormal(chars)<<std::endl;
|
||||
plate.decodePlateNormal(chars);
|
||||
|
||||
cv::String txt = plate.getPlateName();
|
||||
// printf("res:%s\n", txt.c_str());
|
||||
|
||||
//
|
||||
// 写入结果到文件
|
||||
// FILE *fp;
|
||||
// fp = fopen(resSaveFile, "wb+");
|
||||
// fprintf(fp, "%s", txt.c_str());
|
||||
// fclose(fp);
|
||||
//
|
||||
|
||||
delete(recognizer);
|
||||
return txt;
|
||||
}
|
||||
|
||||
Php::Value myFunction(Php::Parameters ¶ms) {
|
||||
|
||||
std::string str = params[0];
|
||||
const char *str_c = str.c_str();
|
||||
Php::Value funcWrapper(Php::Parameters ¶ms) {
|
||||
// 图片路径
|
||||
std::string img = params[0];
|
||||
// 模型路径(文件夹)
|
||||
std::string model = params[1];
|
||||
// 可信度要求
|
||||
double confidence = 0.75;
|
||||
|
||||
cv::String res = scan(str_c);
|
||||
return res.c_str();
|
||||
if (params.size() == 3){
|
||||
confidence = (double)params[2];
|
||||
}
|
||||
|
||||
cv::String res = scan(img, model, confidence);
|
||||
return res.c_str();
|
||||
}
|
||||
|
||||
|
||||
@@ -113,7 +95,11 @@ extern "C" {
|
||||
static Php::Extension extension("platescan", "1.0");
|
||||
|
||||
// @todo add your own functions, classes, namespaces to the extension
|
||||
extension.add<myFunction>("platescan", {Php::ByRef("string", Php::Type::String)});
|
||||
extension.add<funcWrapper>("platescan", {
|
||||
Php::ByVal("imgpath", Php::Type::String, true),
|
||||
Php::ByVal("modelpath", Php::Type::String, true),
|
||||
Php::ByVal("confidence", Php::Type::Float, false)
|
||||
});
|
||||
|
||||
// return the extension
|
||||
return extension;
|
||||
|
||||
Binary file not shown.
@@ -0,0 +1,123 @@
|
||||
input: "data"
|
||||
input_dim: 1
|
||||
input_dim: 1
|
||||
input_dim: 30
|
||||
input_dim: 14
|
||||
layer {
|
||||
name: "conv2d_1"
|
||||
type: "Convolution"
|
||||
bottom: "data"
|
||||
top: "conv2d_1"
|
||||
convolution_param {
|
||||
num_output: 32
|
||||
bias_term: true
|
||||
pad: 0
|
||||
kernel_size: 3
|
||||
stride: 1
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "activation_1"
|
||||
type: "ReLU"
|
||||
bottom: "conv2d_1"
|
||||
top: "activation_1"
|
||||
}
|
||||
layer {
|
||||
name: "max_pooling2d_1"
|
||||
type: "Pooling"
|
||||
bottom: "activation_1"
|
||||
top: "max_pooling2d_1"
|
||||
pooling_param {
|
||||
pool: MAX
|
||||
kernel_size: 2
|
||||
stride: 2
|
||||
pad: 0
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "conv2d_2"
|
||||
type: "Convolution"
|
||||
bottom: "max_pooling2d_1"
|
||||
top: "conv2d_2"
|
||||
convolution_param {
|
||||
num_output: 64
|
||||
bias_term: true
|
||||
pad: 0
|
||||
kernel_size: 3
|
||||
stride: 1
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "activation_2"
|
||||
type: "ReLU"
|
||||
bottom: "conv2d_2"
|
||||
top: "activation_2"
|
||||
}
|
||||
layer {
|
||||
name: "max_pooling2d_2"
|
||||
type: "Pooling"
|
||||
bottom: "activation_2"
|
||||
top: "max_pooling2d_2"
|
||||
pooling_param {
|
||||
pool: MAX
|
||||
kernel_size: 2
|
||||
stride: 2
|
||||
pad: 0
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "conv2d_3"
|
||||
type: "Convolution"
|
||||
bottom: "max_pooling2d_2"
|
||||
top: "conv2d_3"
|
||||
convolution_param {
|
||||
num_output: 128
|
||||
bias_term: true
|
||||
pad: 0
|
||||
kernel_size: 2
|
||||
stride: 1
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "activation_3"
|
||||
type: "ReLU"
|
||||
bottom: "conv2d_3"
|
||||
top: "activation_3"
|
||||
}
|
||||
layer {
|
||||
name: "flatten_1"
|
||||
type: "Flatten"
|
||||
bottom: "activation_3"
|
||||
top: "flatten_1"
|
||||
}
|
||||
layer {
|
||||
name: "dense_1"
|
||||
type: "InnerProduct"
|
||||
bottom: "flatten_1"
|
||||
top: "dense_1"
|
||||
inner_product_param {
|
||||
num_output: 256
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "relu2"
|
||||
type: "ReLU"
|
||||
bottom: "dense_1"
|
||||
top: "relu2"
|
||||
}
|
||||
layer {
|
||||
name: "dense2"
|
||||
type: "InnerProduct"
|
||||
bottom: "relu2"
|
||||
top: "dense2"
|
||||
inner_product_param {
|
||||
num_output: 65
|
||||
}
|
||||
}
|
||||
|
||||
layer {
|
||||
name: "prob"
|
||||
type: "Softmax"
|
||||
bottom: "dense2"
|
||||
top: "prob"
|
||||
}
|
||||
Binary file not shown.
@@ -0,0 +1,95 @@
|
||||
input: "data"
|
||||
input_dim: 1
|
||||
input_dim: 3
|
||||
input_dim: 16
|
||||
input_dim: 66
|
||||
layer {
|
||||
name: "conv1"
|
||||
type: "Convolution"
|
||||
bottom: "data"
|
||||
top: "conv1"
|
||||
convolution_param {
|
||||
num_output: 10
|
||||
bias_term: true
|
||||
pad: 0
|
||||
kernel_size: 3
|
||||
stride: 1
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "relu1"
|
||||
type: "ReLU"
|
||||
bottom: "conv1"
|
||||
top: "conv1"
|
||||
}
|
||||
layer {
|
||||
name: "max_pooling2d_3"
|
||||
type: "Pooling"
|
||||
bottom: "conv1"
|
||||
top: "max_pooling2d_3"
|
||||
pooling_param {
|
||||
pool: MAX
|
||||
kernel_size: 2
|
||||
stride: 2
|
||||
pad: 0
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "conv2"
|
||||
type: "Convolution"
|
||||
bottom: "max_pooling2d_3"
|
||||
top: "conv2"
|
||||
convolution_param {
|
||||
num_output: 16
|
||||
bias_term: true
|
||||
pad: 0
|
||||
kernel_size: 3
|
||||
stride: 1
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "relu2"
|
||||
type: "ReLU"
|
||||
bottom: "conv2"
|
||||
top: "conv2"
|
||||
}
|
||||
layer {
|
||||
name: "conv3"
|
||||
type: "Convolution"
|
||||
bottom: "conv2"
|
||||
top: "conv3"
|
||||
convolution_param {
|
||||
num_output: 32
|
||||
bias_term: true
|
||||
pad: 0
|
||||
kernel_size: 3
|
||||
stride: 1
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "relu3"
|
||||
type: "ReLU"
|
||||
bottom: "conv3"
|
||||
top: "conv3"
|
||||
}
|
||||
layer {
|
||||
name: "flatten_2"
|
||||
type: "Flatten"
|
||||
bottom: "conv3"
|
||||
top: "flatten_2"
|
||||
}
|
||||
layer {
|
||||
name: "dense"
|
||||
type: "InnerProduct"
|
||||
bottom: "flatten_2"
|
||||
top: "dense"
|
||||
inner_product_param {
|
||||
num_output: 2
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "relu4"
|
||||
type: "ReLU"
|
||||
bottom: "dense"
|
||||
top: "dense"
|
||||
}
|
||||
Binary file not shown.
@@ -0,0 +1,114 @@
|
||||
input: "data"
|
||||
input_dim: 1
|
||||
input_dim: 1
|
||||
input_dim: 22
|
||||
input_dim: 22
|
||||
layer {
|
||||
name: "conv2d_12"
|
||||
type: "Convolution"
|
||||
bottom: "data"
|
||||
top: "conv2d_12"
|
||||
convolution_param {
|
||||
num_output: 16
|
||||
bias_term: true
|
||||
pad: 0
|
||||
kernel_size: 3
|
||||
stride: 1
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "activation_18"
|
||||
type: "ReLU"
|
||||
bottom: "conv2d_12"
|
||||
top: "activation_18"
|
||||
}
|
||||
layer {
|
||||
name: "max_pooling2d_10"
|
||||
type: "Pooling"
|
||||
bottom: "activation_18"
|
||||
top: "max_pooling2d_10"
|
||||
pooling_param {
|
||||
pool: MAX
|
||||
kernel_size: 2
|
||||
stride: 2
|
||||
pad: 0
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "conv2d_13"
|
||||
type: "Convolution"
|
||||
bottom: "max_pooling2d_10"
|
||||
top: "conv2d_13"
|
||||
convolution_param {
|
||||
num_output: 16
|
||||
bias_term: true
|
||||
pad: 0
|
||||
kernel_size: 3
|
||||
stride: 1
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "activation_19"
|
||||
type: "ReLU"
|
||||
bottom: "conv2d_13"
|
||||
top: "activation_19"
|
||||
}
|
||||
layer {
|
||||
name: "max_pooling2d_11"
|
||||
type: "Pooling"
|
||||
bottom: "activation_19"
|
||||
top: "max_pooling2d_11"
|
||||
pooling_param {
|
||||
pool: MAX
|
||||
kernel_size: 2
|
||||
stride: 2
|
||||
pad: 0
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "flatten_6"
|
||||
type: "Flatten"
|
||||
bottom: "max_pooling2d_11"
|
||||
top: "flatten_6"
|
||||
}
|
||||
layer {
|
||||
name: "dense_9"
|
||||
type: "InnerProduct"
|
||||
bottom: "flatten_6"
|
||||
top: "dense_9"
|
||||
inner_product_param {
|
||||
num_output: 256
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "dropout_9"
|
||||
type: "Dropout"
|
||||
bottom: "dense_9"
|
||||
top: "dropout_9"
|
||||
dropout_param {
|
||||
dropout_ratio: 0.5
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "activation_20"
|
||||
type: "ReLU"
|
||||
bottom: "dropout_9"
|
||||
top: "activation_20"
|
||||
}
|
||||
layer {
|
||||
name: "dense_10"
|
||||
type: "InnerProduct"
|
||||
bottom: "activation_20"
|
||||
top: "dense_10"
|
||||
inner_product_param {
|
||||
num_output: 3
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
layer {
|
||||
name: "prob"
|
||||
type: "Softmax"
|
||||
bottom: "dense_10"
|
||||
top: "prob"
|
||||
}
|
||||
Binary file not shown.
@@ -0,0 +1,318 @@
|
||||
input: "data"
|
||||
input_dim: 1
|
||||
input_dim: 3
|
||||
input_dim: 160
|
||||
input_dim: 40
|
||||
layer {
|
||||
name: "conv0"
|
||||
type: "Convolution"
|
||||
bottom: "data"
|
||||
top: "conv0"
|
||||
convolution_param {
|
||||
num_output: 32
|
||||
bias_term: true
|
||||
pad_h: 1
|
||||
pad_w: 1
|
||||
kernel_h: 3
|
||||
kernel_w: 3
|
||||
stride_h: 1
|
||||
stride_w: 1
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "bn0"
|
||||
type: "BatchNorm"
|
||||
bottom: "conv0"
|
||||
top: "bn0"
|
||||
batch_norm_param {
|
||||
moving_average_fraction: 0.99
|
||||
eps: 0.001
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "bn0_scale"
|
||||
type: "Scale"
|
||||
bottom: "bn0"
|
||||
top: "bn0"
|
||||
scale_param {
|
||||
bias_term: true
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "relu0"
|
||||
type: "ReLU"
|
||||
bottom: "bn0"
|
||||
top: "bn0"
|
||||
}
|
||||
layer {
|
||||
name: "pool0"
|
||||
type: "Pooling"
|
||||
bottom: "bn0"
|
||||
top: "pool0"
|
||||
pooling_param {
|
||||
pool: MAX
|
||||
kernel_h: 2
|
||||
kernel_w: 2
|
||||
stride_h: 2
|
||||
stride_w: 2
|
||||
pad_h: 0
|
||||
pad_w: 0
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "conv1"
|
||||
type: "Convolution"
|
||||
bottom: "pool0"
|
||||
top: "conv1"
|
||||
convolution_param {
|
||||
num_output: 64
|
||||
bias_term: true
|
||||
pad_h: 1
|
||||
pad_w: 1
|
||||
kernel_h: 3
|
||||
kernel_w: 3
|
||||
stride_h: 1
|
||||
stride_w: 1
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "bn1"
|
||||
type: "BatchNorm"
|
||||
bottom: "conv1"
|
||||
top: "bn1"
|
||||
batch_norm_param {
|
||||
moving_average_fraction: 0.99
|
||||
eps: 0.001
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "bn1_scale"
|
||||
type: "Scale"
|
||||
bottom: "bn1"
|
||||
top: "bn1"
|
||||
scale_param {
|
||||
bias_term: true
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "relu1"
|
||||
type: "ReLU"
|
||||
bottom: "bn1"
|
||||
top: "bn1"
|
||||
}
|
||||
layer {
|
||||
name: "pool1"
|
||||
type: "Pooling"
|
||||
bottom: "bn1"
|
||||
top: "pool1"
|
||||
pooling_param {
|
||||
pool: MAX
|
||||
kernel_h: 2
|
||||
kernel_w: 2
|
||||
stride_h: 2
|
||||
stride_w: 2
|
||||
pad_h: 0
|
||||
pad_w: 0
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "conv2"
|
||||
type: "Convolution"
|
||||
bottom: "pool1"
|
||||
top: "conv2"
|
||||
convolution_param {
|
||||
num_output: 128
|
||||
bias_term: true
|
||||
pad_h: 1
|
||||
pad_w: 1
|
||||
kernel_h: 3
|
||||
kernel_w: 3
|
||||
stride_h: 1
|
||||
stride_w: 1
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "bn2"
|
||||
type: "BatchNorm"
|
||||
bottom: "conv2"
|
||||
top: "bn2"
|
||||
batch_norm_param {
|
||||
moving_average_fraction: 0.99
|
||||
eps: 0.001
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "bn2_scale"
|
||||
type: "Scale"
|
||||
bottom: "bn2"
|
||||
top: "bn2"
|
||||
scale_param {
|
||||
bias_term: true
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "relu2"
|
||||
type: "ReLU"
|
||||
bottom: "bn2"
|
||||
top: "bn2"
|
||||
}
|
||||
layer {
|
||||
name: "pool2"
|
||||
type: "Pooling"
|
||||
bottom: "bn2"
|
||||
top: "pool2"
|
||||
pooling_param {
|
||||
pool: MAX
|
||||
kernel_h: 2
|
||||
kernel_w: 2
|
||||
stride_h: 2
|
||||
stride_w: 2
|
||||
pad_h: 0
|
||||
pad_w: 0
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "conv_512_15"
|
||||
type: "Convolution"
|
||||
bottom: "pool2"
|
||||
top: "conv_512_15"
|
||||
convolution_param {
|
||||
num_output: 512
|
||||
bias_term: true
|
||||
pad_h: 0
|
||||
pad_w: 0
|
||||
kernel_h: 1
|
||||
kernel_w: 5
|
||||
stride_h: 1
|
||||
stride_w: 1
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "batch_normalization_1"
|
||||
type: "BatchNorm"
|
||||
bottom: "conv_512_15"
|
||||
top: "batch_normalization_1"
|
||||
batch_norm_param {
|
||||
moving_average_fraction: 0.99
|
||||
eps: 0.001
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "batch_normalization_1_scale"
|
||||
type: "Scale"
|
||||
bottom: "batch_normalization_1"
|
||||
top: "batch_normalization_1"
|
||||
scale_param {
|
||||
bias_term: true
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "activation_1"
|
||||
type: "ReLU"
|
||||
bottom: "batch_normalization_1"
|
||||
top: "batch_normalization_1"
|
||||
}
|
||||
layer {
|
||||
name: "conv_512_51"
|
||||
type: "Convolution"
|
||||
bottom: "batch_normalization_1"
|
||||
top: "conv_512_51"
|
||||
convolution_param {
|
||||
num_output: 512
|
||||
bias_term: true
|
||||
pad_h: 0
|
||||
pad_w: 0
|
||||
kernel_h: 5
|
||||
kernel_w: 1
|
||||
stride_h: 1
|
||||
stride_w: 1
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "batch_normalization_2"
|
||||
type: "BatchNorm"
|
||||
bottom: "conv_512_51"
|
||||
top: "batch_normalization_2"
|
||||
batch_norm_param {
|
||||
moving_average_fraction: 0.99
|
||||
eps: 0.001
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "batch_normalization_2_scale"
|
||||
type: "Scale"
|
||||
bottom: "batch_normalization_2"
|
||||
top: "batch_normalization_2"
|
||||
scale_param {
|
||||
bias_term: true
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "activation_2"
|
||||
type: "ReLU"
|
||||
bottom: "batch_normalization_2"
|
||||
top: "batch_normalization_2"
|
||||
}
|
||||
layer {
|
||||
name: "conv_1024_11"
|
||||
type: "Convolution"
|
||||
bottom: "batch_normalization_2"
|
||||
top: "conv_1024_11"
|
||||
convolution_param {
|
||||
num_output: 1024
|
||||
bias_term: true
|
||||
pad_h: 0
|
||||
pad_w: 0
|
||||
kernel_h: 1
|
||||
kernel_w: 1
|
||||
stride_h: 1
|
||||
stride_w: 1
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "batch_normalization_3"
|
||||
type: "BatchNorm"
|
||||
bottom: "conv_1024_11"
|
||||
top: "batch_normalization_3"
|
||||
batch_norm_param {
|
||||
moving_average_fraction: 0.99
|
||||
eps: 0.001
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "batch_normalization_3_scale"
|
||||
type: "Scale"
|
||||
bottom: "batch_normalization_3"
|
||||
top: "batch_normalization_3"
|
||||
scale_param {
|
||||
bias_term: true
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "activation_3"
|
||||
type: "ReLU"
|
||||
bottom: "batch_normalization_3"
|
||||
top: "batch_normalization_3"
|
||||
}
|
||||
layer {
|
||||
name: "conv_class_11"
|
||||
type: "Convolution"
|
||||
bottom: "batch_normalization_3"
|
||||
top: "conv_class_11"
|
||||
convolution_param {
|
||||
num_output: 84
|
||||
bias_term: true
|
||||
pad_h: 0
|
||||
pad_w: 0
|
||||
kernel_h: 1
|
||||
kernel_w: 1
|
||||
stride_h: 1
|
||||
stride_w: 1
|
||||
}
|
||||
}
|
||||
layer {
|
||||
name: "prob"
|
||||
type: "Softmax"
|
||||
bottom: "conv_class_11"
|
||||
top: "prob"
|
||||
}
|
||||
File diff suppressed because it is too large
Load Diff
@@ -1,13 +1,13 @@
|
||||
<?php
|
||||
//
|
||||
// Created by Coleflowers on 20/06/2018.
|
||||
// Updated by JustID on 03/07/2018.
|
||||
//
|
||||
|
||||
/**
|
||||
* 车牌识别PHP扩展程序测试
|
||||
*/
|
||||
$path = realpath("demo.png");
|
||||
$res = platescan($path);
|
||||
$res = platescan(realpath("demo.png"),realpath("model"),0.8);
|
||||
var_dump($res);
|
||||
|
||||
?>
|
||||
|
||||
Reference in New Issue
Block a user