mirror of
https://github.com/NanjingForestryUniversity/supermachine-tobacco.git
synced 2025-11-08 22:33:54 +00:00
[ext] 修改transmit到一半
This commit is contained in:
parent
e7e7de43e6
commit
c076e04f57
53
README.md
53
README.md
@ -4,6 +4,7 @@
|
||||
|
||||
## 如何进行模型训练和部署?
|
||||
1. 项目当中需要包含`data`和`models`这两个文件夹,请下载到当前文件夹下,这是链接:[data](https://macrosolid-my.sharepoint.com/personal/feijinti_miaow_fun/_layouts/15/onedrive.aspx?id=%2Fpersonal%2Ffeijinti%5Fmiaow%5Ffun%2FDocuments%2FPycharmProjects%2Ftobacco%5Fcolor%2Fdata&ga=1), [models](https://macrosolid-my.sharepoint.com/:f:/g/personal/feijinti_miaow_fun/EiyBjWEX90JGn8S-e5Kh7N8B1GWvfvDcNbpleWDTwkDm1w?e=wyL4EF)
|
||||
|
||||
2. 使用[01_dataset.ipynb](./01_dataset.ipynb) 进行数据集的分析文件格式需要设置为这种形式:
|
||||
```text
|
||||
dataset
|
||||
@ -14,11 +15,63 @@
|
||||
├── img1.bmp
|
||||
└── ...
|
||||
```
|
||||
|
||||
3. 使用[02_classification.ipynb](./02_classification.ipynb)进行训练
|
||||
|
||||
4. 使用[03_data_update.ipynb](02_classification.ipynb)进行数据的更新与添加
|
||||
|
||||
5. 使用`main_test.py`文件进行读图测试
|
||||
|
||||
6. **部署**,复制`utils.py`、`models.py`、`main.py`、`models/`、`config.py`这5个文件或文件夹,运行main.py来提供预测服务。
|
||||
|
||||
## 如何进行参数调节?
|
||||
|
||||
所有的参数均位于项目文件夹下的`config.py`当中。
|
||||
|
||||
```python
|
||||
class Config:
|
||||
# 文件相关参数
|
||||
nRows, nCols, nBands = 256, 1024, 22
|
||||
nRgbRows, nRgbCols, nRgbBands = 1024, 4096, 3
|
||||
|
||||
# 需要设置的谱段等参数
|
||||
selected_bands = [127, 201, 202, 294]
|
||||
bands = [127, 200, 201, 202, 203, 204, 205, 206, 207, 208, 209, 210,
|
||||
211, 212, 213, 214, 215, 216, 217, 218, 219, 294]
|
||||
is_yellow_min = np.array([0.10167048, 0.1644719, 0.1598884, 0.31534621])
|
||||
is_yellow_max = np.array([0.212984, 0.25896924, 0.26509268, 0.51943593])
|
||||
is_black_threshold = np.asarray([0.1369, 0.1472, 0.1439, 0.1814])
|
||||
black_yellow_bands = [0, 2, 3, 21]
|
||||
green_bands = [i for i in range(1, 21)]
|
||||
|
||||
# 光谱模型参数
|
||||
blk_size = 4 # 必须是2的倍数,不然会出错
|
||||
pixel_model_path = r"./models/pixel_2022-08-02_15-22.model"
|
||||
blk_model_path = r"./models/rf_4x4_c22_20_sen8_9.model"
|
||||
spec_size_threshold = 3 # 光谱大小阈值
|
||||
|
||||
# rgb模型参数
|
||||
rgb_tobacco_model_path = r"models/tobacco_dt_2022-08-05_10-38.model"
|
||||
rgb_background_model_path = r"models/background_dt_2022-08-09_16-08.model"
|
||||
threshold_low, threshold_high = 10, 230 # 亮度最高值和最低值
|
||||
threshold_s = 190 # 饱和度最高值允许值,超过该饱和度会被当作杂质
|
||||
rgb_size_threshold = 4 # RGB大小阈值(在运行时会被界面修改)
|
||||
|
||||
# mask parameter
|
||||
target_size = (1024, 1024) # (Width, Height) of mask
|
||||
valve_merge_size = 2 # 每两个喷阀当中有任意一个出现杂质则认为都是杂质
|
||||
valve_horizontal_padding = 3 # 喷阀横向膨胀的尺寸,应该是奇数,3时表示左右各膨胀1
|
||||
max_open_valve_limit = 25 # 最大同时开启喷阀限制,按照电流计算,当前的喷阀可以开启的喷阀 600W的电源 / 12V电源 = 50A, 一个阀门1A
|
||||
|
||||
# save part
|
||||
offset_vertical = 0
|
||||
|
||||
# logging
|
||||
root_dir = os.path.split(os.path.realpath(__file__))[0]
|
||||
```
|
||||
|
||||
|
||||
|
||||
|
||||
## 训练的原理
|
||||
为了应对工业环境当中负样本少的特点,我们结合颜色有限空间的特性对我们的训练过程进行了优化,核心的优化方式在于制造负样本。
|
||||
|
||||
80
transmit.py
80
transmit.py
@ -1,7 +1,10 @@
|
||||
import multiprocessing
|
||||
import os
|
||||
import threading
|
||||
from multiprocessing import Process, Queue
|
||||
import time
|
||||
from multiprocessing.synchronize import Lock
|
||||
from threading import Lock
|
||||
|
||||
import cv2
|
||||
|
||||
@ -11,13 +14,15 @@ import functools
|
||||
import numpy as np
|
||||
from config import Config
|
||||
from models import SpecDetector, RgbDetector
|
||||
from typing import Any
|
||||
from typing import Any, Union
|
||||
import logging
|
||||
logging.basicConfig(format='%(asctime)s %(levelname)s %(name)s %(message)s',
|
||||
level=logging.WARNING)
|
||||
|
||||
|
||||
class Transmitter(object):
|
||||
_io_lock: Union[Lock, Lock]
|
||||
|
||||
def __init__(self, job_name:str, run_process:bool = False):
|
||||
self.output = None
|
||||
self.job_name = job_name
|
||||
@ -25,6 +30,7 @@ class Transmitter(object):
|
||||
self._thread_stop = threading.Event()
|
||||
self._thread_stop.clear()
|
||||
self._running_handler = None
|
||||
self._io_lock = multiprocessing.Lock() if run_process else threading.Lock()
|
||||
|
||||
def set_source(self, *args, **kwargs):
|
||||
"""
|
||||
@ -35,13 +41,13 @@ class Transmitter(object):
|
||||
"""
|
||||
raise NotImplementedError
|
||||
|
||||
def set_output(self, output: ImgQueue):
|
||||
def set_output(self, *args, **kwargs):
|
||||
"""
|
||||
设置单个输出源
|
||||
设置输出源
|
||||
:param output:
|
||||
:return:
|
||||
"""
|
||||
self.output = output
|
||||
raise NotImplementedError
|
||||
|
||||
def start(self, *args, **kwargs):
|
||||
"""
|
||||
@ -113,6 +119,44 @@ class BeforeAfterMethods:
|
||||
return rgb_img
|
||||
|
||||
|
||||
class FileReceiver(Transmitter):
|
||||
def __init__(self, job_name:str, input_dir: str, output_queue:ImgQueue, speed: int=3, name_pattern=None):
|
||||
super(FileReceiver, self).__init__(job_name=job_name, run_process=False)
|
||||
self.input_dir = input_dir
|
||||
self.send_speed = speed
|
||||
self.file_names = None
|
||||
self.name_pattern = name_pattern
|
||||
self.file_idx = 0
|
||||
self.output_queue = None
|
||||
self.set_source(input_dir, name_pattern)
|
||||
self.set_output(output_queue)
|
||||
|
||||
def set_source(self, input_dir, name_pattern=None):
|
||||
self.name_pattern = name_pattern if name_pattern is not None else self.name_pattern
|
||||
file_names = os.listdir(input_dir)
|
||||
if len(file_names) == 0:
|
||||
logging.warning('指定了空的文件夹')
|
||||
if self.name_pattern is not None:
|
||||
file_names = [file_name for file_name in file_names if (self.name_pattern in file_name)]
|
||||
else:
|
||||
file_names = file_names
|
||||
|
||||
with self._io_lock:
|
||||
self.file_names = file_names
|
||||
self.file_idx = 0
|
||||
|
||||
def set_output(self, output: ImgQueue):
|
||||
with self._io_lock:
|
||||
self.output_queue = output
|
||||
|
||||
@Transmitter.job_decorator
|
||||
def job_func(self, *args, **kwargs):
|
||||
with self._io_lock:
|
||||
self.file_idx += 1
|
||||
if self.file_idx == len()
|
||||
file_name = self.file_names[self.file_idx]
|
||||
|
||||
|
||||
class FifoReceiver(Transmitter):
|
||||
def __init__(self, job_name:str, fifo_path: str, output: ImgQueue,
|
||||
read_max_num: int, msg_queue=None):
|
||||
@ -169,31 +213,23 @@ class FifoSender(Transmitter):
|
||||
os.mkfifo(output_fifo_path, 0o777)
|
||||
self._output_fifo_path = output_fifo_path
|
||||
|
||||
def start(self, pre_process=None, name='fifo_receiver'):
|
||||
self._running_thread = threading.Thread(target=self._send_thread_func, name=name,
|
||||
args=(pre_process, ))
|
||||
self._running_thread.start()
|
||||
|
||||
def stop(self):
|
||||
self._need_stop.set()
|
||||
|
||||
def _send_thread_func(self, pre_process=None):
|
||||
def job_func(self, pre_process, *args, **kwargs):
|
||||
"""
|
||||
接收线程
|
||||
|
||||
:param pre_process:
|
||||
:return:
|
||||
"""
|
||||
while not self._need_stop.is_set():
|
||||
if self._input_source.empty():
|
||||
continue
|
||||
data = self._input_source.get()
|
||||
if pre_process is not None:
|
||||
data = pre_process(data)
|
||||
output_fifo = os.open(self._output_fifo_path, os.O_WRONLY)
|
||||
os.write(output_fifo, data)
|
||||
os.close(output_fifo)
|
||||
self._need_stop.clear()
|
||||
if self._input_source.empty():
|
||||
return
|
||||
data = self._input_source.get()
|
||||
if pre_process is not None:
|
||||
data = pre_process(data)
|
||||
output_fifo = os.open(self._output_fifo_path, os.O_WRONLY)
|
||||
os.write(output_fifo, data)
|
||||
os.close(output_fifo)
|
||||
|
||||
|
||||
def __del__(self):
|
||||
self.stop()
|
||||
|
||||
Loading…
Reference in New Issue
Block a user