1、首先从官方下载mask_rcnn源码https://github.com/matterport/Mask_RCNN

2、当制作自己的数据集的时候,图片的大小一定要记得修改,长宽都要修改为修改为2的6次方的倍数,不然训练的时候会报错,来看源代码:

2、首先将demo.ipynb转换成demo.py,这里我顺便更改为适用于我自己数据集:

import os
import sys
import random
import math
import numpy as np
import skimage.io
import matplotlib
import matplotlib.pyplot as plt
import cv2
import time
from mrcnn.config import Config
from datetime import datetime
# Root directory of the project
ROOT_DIR = os.path.abspath("../") # Import Mask RCNN
sys.path.append(ROOT_DIR) # To find local version of the library
from mrcnn import utils
import mrcnn.model as modellib
from mrcnn import visualize
# Import COCO config
sys.path.append(os.path.join(ROOT_DIR, "samples/coco/")) # To find local version
import coco # Directory to save logs and trained model
MODEL_DIR = os.path.join(ROOT_DIR, "logs/shapes20190425T0816") # Local path to trained weights file
COCO_MODEL_PATH = os.path.join(MODEL_DIR ,"mask_rcnn_shapes_0030.h5")
# Download COCO trained weights from Releases if needed
if not os.path.exists(COCO_MODEL_PATH):
utils.download_trained_weights(COCO_MODEL_PATH)
print("cuiwei***********************") # Directory of images to run detection on
IMAGE_DIR = os.path.join(ROOT_DIR, "images")
class ShapesConfig(Config):
"""Configuration for training on the toy shapes dataset.
Derives from the base Config class and overrides values specific
to the toy shapes dataset.
"""
# Give the configuration a recognizable name
NAME = "shapes" # Train on 1 GPU and 8 images per GPU. We can put multiple images on each
# GPU because the images are small. Batch size is 8 (GPUs * images/GPU).
GPU_COUNT = 1
IMAGES_PER_GPU = 1 # Number of classes (including background)
NUM_CLASSES = 1 + 4 # background + 3 shapes # Use small images for faster training. Set the limits of the small side
# the large side, and that determines the image shape.
IMAGE_MIN_DIM = 320
IMAGE_MAX_DIM = 384 # Use smaller anchors because our image and objects are small
RPN_ANCHOR_SCALES = (8 * 6, 16 * 6, 32 * 6, 64 * 6, 128 * 6) # anchor side in pixels # Reduce training ROIs per image because the images are small and have
# few objects. Aim to allow ROI sampling to pick 33% positive ROIs.
TRAIN_ROIS_PER_IMAGE =100 # Use a small epoch since the data is simple
STEPS_PER_EPOCH = 100 # use small validation steps since the epoch is small
VALIDATION_STEPS = 50 class InferenceConfig(ShapesConfig):
# Set batch size to 1 since we'll be running inference on
# one image at a time. Batch size = GPU_COUNT * IMAGES_PER_GPU
GPU_COUNT = 1
IMAGES_PER_GPU = 1 config = InferenceConfig()
config.display() # Create model object in inference mode.
model = modellib.MaskRCNN(mode="inference", model_dir=MODEL_DIR, config=config) # Load weights trained on MS-COCO
model.load_weights(COCO_MODEL_PATH, by_name=True) # COCO Class names
# Index of the class in the list is its ID. For example, to get ID of
# the teddy bear class, use: class_names.index('teddy bear')
class_names = ['BG', 'a','b','c','e']
# Load a random image from the images folder
#file_names = next(os.walk(IMAGE_DIR))[2]
#image = skimage.io.imread(os.path.join(IMAGE_DIR, random.choice(file_names)))
cap = cv2.VideoCapture(0) while(1):
# get a frame
ret, frame = cap.read()
# show a frame
start =time.clock()
results = model.detect([frame], verbose=1)
r = results[0]
#cv2.imshow("capture", frame)
visualize.display_instances(frame, r['rois'], r['masks'], r['class_ids'],
class_names, r['scores'])
end = time.clock()
print(end-start)
if cv2.waitKey(1) & 0xFF == ord('q'):
break cap.release()
cv2.destroyAllWindows() #image= cv2.imread("C:\\Users\\18301\\Desktop\\Mask_RCNN-master\\images\\9.jpg")
## Run detection
#
#results = model.detect([image], verbose=1)
#
#print(end-start)
## Visualize results
#r = results[0]
#visualize.display_instances(image, r['rois'], r['masks'], r['class_ids'],
# class_names, r['scores'])

以上这段代码可以调用摄像头拍摄图片进行目标识别。

以下为训练文件:

# -*- coding: utf-8 -*-

import os
import sys
import random
import math
import re
import time
import numpy as np
import cv2
import matplotlib
import matplotlib.pyplot as plt
import tensorflow as tf
from mrcnn.config import Config
#import utils
from mrcnn import model as modellib,utils
from mrcnn import visualize
import yaml
from mrcnn.model import log
from PIL import Image #os.environ["CUDA_VISIBLE_DEVICES"] = "0"
# Root directory of the project
ROOT_DIR = os.getcwd() #ROOT_DIR = os.path.abspath("../")
# Directory to save logs and trained model
MODEL_DIR = os.path.join(ROOT_DIR, "logs") iter_num=0 # Local path to trained weights file
COCO_MODEL_PATH = os.path.join(ROOT_DIR, "mask_rcnn_coco.h5")
# Download COCO trained weights from Releases if needed
if not os.path.exists(COCO_MODEL_PATH):
utils.download_trained_weights(COCO_MODEL_PATH) class ShapesConfig(Config):
"""Configuration for training on the toy shapes dataset.
Derives from the base Config class and overrides values specific
to the toy shapes dataset.
"""
# Give the configuration a recognizable name
NAME = "shapes" # Train on 1 GPU and 8 images per GPU. We can put multiple images on each
# GPU because the images are small. Batch size is 8 (GPUs * images/GPU).
GPU_COUNT = 1
IMAGES_PER_GPU = 1 # Number of classes (including background)
NUM_CLASSES = 1 + 4 # background + 3 shapes # Use small images for faster training. Set the limits of the small side
# the large side, and that determines the image shape.
IMAGE_MIN_DIM = 320
IMAGE_MAX_DIM = 384 # Use smaller anchors because our image and objects are small
RPN_ANCHOR_SCALES = (8 * 6, 16 * 6, 32 * 6, 64 * 6, 128 * 6) # anchor side in pixels # Reduce training ROIs per image because the images are small and have
# few objects. Aim to allow ROI sampling to pick 33% positive ROIs.
TRAIN_ROIS_PER_IMAGE = 100 # Use a small epoch since the data is simple
STEPS_PER_EPOCH = 100 # use small validation steps since the epoch is small
VALIDATION_STEPS = 50 config = ShapesConfig()
config.display() class DrugDataset(utils.Dataset):
# 得到该图中有多少个实例(物体)
def get_obj_index(self, image):
n = np.max(image)
return n # 解析labelme中得到的yaml文件,从而得到mask每一层对应的实例标签
def from_yaml_get_class(self, image_id):
info = self.image_info[image_id]
with open(info['yaml_path']) as f:
temp = yaml.load(f.read())
labels = temp['label_names']
del labels[0]
return labels # 重新写draw_mask
def draw_mask(self, num_obj, mask, image,image_id):
#print("draw_mask-->",image_id)
#print("self.image_info",self.image_info)
info = self.image_info[image_id]
#print("info-->",info)
#print("info[width]----->",info['width'],"-info[height]--->",info['height'])
for index in range(num_obj):
for i in range(info['width']):
for j in range(info['height']):
#print("image_id-->",image_id,"-i--->",i,"-j--->",j)
#print("info[width]----->",info['width'],"-info[height]--->",info['height'])
at_pixel = image.getpixel((i, j))
if at_pixel == index + 1:
mask[j, i, index] = 1
return mask # 重新写load_shapes,里面包含自己的自己的类别
# 并在self.image_info信息中添加了path、mask_path 、yaml_path
# yaml_pathdataset_root_path = "/tongue_dateset/"
# img_floder = dataset_root_path + "rgb"
# mask_floder = dataset_root_path + "mask"
# dataset_root_path = "/tongue_dateset/"
def load_shapes(self, count, img_floder, mask_floder, imglist, dataset_root_path):
"""Generate the requested number of synthetic images.
count: number of images to generate.
height, width: the size of the generated images.
"""
# Add classes
self.add_class("shapes", 1, "a")
self.add_class("shapes", 2, "b")
self.add_class("shapes", 3, "c")
self.add_class("shapes", 4, "e")
for i in range(count):
# 获取图片宽和高 filestr = imglist[i].split(".")[0]
#print(imglist[i],"-->",cv_img.shape[1],"--->",cv_img.shape[0])
#print("id-->", i, " imglist[", i, "]-->", imglist[i],"filestr-->",filestr)
# filestr = filestr.split("_")[1]
mask_path = mask_floder + "/" + filestr + ".png"
yaml_path = dataset_root_path + "labelme_json/" + filestr + "_json/info.yaml"
print(dataset_root_path + "labelme_json/" + filestr + "_json/img.png")
cv_img = cv2.imread(dataset_root_path + "labelme_json/" + filestr + "_json/img.png") self.add_image("shapes", image_id=i, path=img_floder + "/" + imglist[i],
width=cv_img.shape[1], height=cv_img.shape[0], mask_path=mask_path, yaml_path=yaml_path) # 重写load_mask
def load_mask(self, image_id):
"""Generate instance masks for shapes of the given image ID.
"""
global iter_num
print("image_id",image_id)
info = self.image_info[image_id]
count = 1 # number of object
img = Image.open(info['mask_path'])
num_obj = self.get_obj_index(img)
mask = np.zeros([info['height'], info['width'], num_obj], dtype=np.uint8)
mask = self.draw_mask(num_obj, mask, img,image_id)
occlusion = np.logical_not(mask[:, :, -1]).astype(np.uint8)
for i in range(count - 2, -1, -1):
mask[:, :, i] = mask[:, :, i] * occlusion occlusion = np.logical_and(occlusion, np.logical_not(mask[:, :, i]))
labels = []
labels = self.from_yaml_get_class(image_id)
labels_form = []
for i in range(len(labels)):
if labels[i].find("a") != -1:
labels_form.append("a")
elif labels[i].find("b") != -1:
labels_form.append("b")
elif labels[i].find("c") != -1:
labels_form.append("c")
elif labels[i].find("e") != -1:
labels_form.append("e")
class_ids = np.array([self.class_names.index(s) for s in labels_form])
return mask, class_ids.astype(np.int32) def get_ax(rows=1, cols=1, size=8):
"""Return a Matplotlib Axes array to be used in
all visualizations in the notebook. Provide a
central point to control graph sizes. Change the default size attribute to control the size
of rendered images
"""
_, ax = plt.subplots(rows, cols, figsize=(size * cols, size * rows))
return ax #基础设置
dataset_root_path="train_data/"
img_floder = dataset_root_path + "pic"
mask_floder = dataset_root_path + "cv2_mask"
#yaml_floder = dataset_root_path
imglist = os.listdir(img_floder)
count = len(imglist) #train与val数据集准备
dataset_train = DrugDataset()
dataset_train.load_shapes(count, img_floder, mask_floder, imglist,dataset_root_path)
dataset_train.prepare() #print("dataset_train-->",dataset_train._image_ids) dataset_val = DrugDataset()
dataset_val.load_shapes(7, img_floder, mask_floder, imglist,dataset_root_path)
dataset_val.prepare() #print("dataset_val-->",dataset_val._image_ids) # Load and display random samples
#image_ids = np.random.choice(dataset_train.image_ids, 4)
#for image_id in image_ids:
# image = dataset_train.load_image(image_id)
# mask, class_ids = dataset_train.load_mask(image_id)
# visualize.display_top_masks(image, mask, class_ids, dataset_train.class_names) # Create model in training mode
model = modellib.MaskRCNN(mode="training", config=config,
model_dir=MODEL_DIR) # Which weights to start with?
init_with = "coco" # imagenet, coco, or last if init_with == "imagenet":
model.load_weights(model.get_imagenet_weights(), by_name=True)
elif init_with == "coco":
# Load weights trained on MS COCO, but skip layers that
# are different due to the different number of classes
# See README for instructions to download the COCO weights
model.load_weights(COCO_MODEL_PATH, by_name=True,
exclude=["mrcnn_class_logits", "mrcnn_bbox_fc",
"mrcnn_bbox", "mrcnn_mask"])
elif init_with == "last":
# Load the last model you trained and continue training
model.load_weights(model.find_last()[1], by_name=True) # Train the head branches
# Passing layers="heads" freezes all layers except the head
# layers. You can also pass a regular expression to select
# which layers to train by name pattern.
model.train(dataset_train, dataset_val,
learning_rate=config.LEARNING_RATE,
epochs=10,
layers='heads') # Fine tune all layers
# Passing layers="all" trains all layers. You can also
# pass a regular expression to select which layers to
# train by name pattern.
model.train(dataset_train, dataset_val,
learning_rate=config.LEARNING_RATE / 10,
epochs=30,
layers="all")

以下为测试代码:

# -*- coding: utf-8 -*-

import os
import sys
import random
import math
import numpy as np
import skimage.io
import matplotlib
import matplotlib.pyplot as plt
import cv2
import time
from mrcnn.config import Config
from datetime import datetime
# Root directory of the project
ROOT_DIR = os.getcwd() # Import Mask RCNN
sys.path.append(ROOT_DIR) # To find local version of the library
from mrcnn import utils
import mrcnn.model as modellib
from mrcnn import visualize
# Import COCO config
sys.path.append(os.path.join(ROOT_DIR, "samples/coco/")) # To find local version
from samples.coco import coco # Directory to save logs and trained model
MODEL_DIR = os.path.join(ROOT_DIR, "logs/shapes20190425T0816/") # Local path to trained weights file
COCO_MODEL_PATH = os.path.join(MODEL_DIR ,"mask_rcnn_shapes_0030.h5")
# Download COCO trained weights from Releases if needed
if not os.path.exists(COCO_MODEL_PATH):
utils.download_trained_weights(COCO_MODEL_PATH)
print("wancheng***********************") # Directory of images to run detection on
IMAGE_DIR = os.path.join(ROOT_DIR, "images") class ShapesConfig(Config):
"""Configuration for training on the toy shapes dataset.
Derives from the base Config class and overrides values specific
to the toy shapes dataset.
"""
# Give the configuration a recognizable name
NAME = "shapes" # Train on 1 GPU and 8 images per GPU. We can put multiple images on each
# GPU because the images are small. Batch size is 8 (GPUs * images/GPU).
GPU_COUNT = 1
IMAGES_PER_GPU = 1 # Number of classes (including background)
NUM_CLASSES = 1 + 4 # background + 3 shapes # Use small images for faster training. Set the limits of the small side
# the large side, and that determines the image shape.
IMAGE_MIN_DIM = 320
IMAGE_MAX_DIM = 384 # Use smaller anchors because our image and objects are small
RPN_ANCHOR_SCALES = (8 * 6, 16 * 6, 32 * 6, 64 * 6, 128 * 6) # anchor side in pixels # Reduce training ROIs per image because the images are small and have
# few objects. Aim to allow ROI sampling to pick 33% positive ROIs.
TRAIN_ROIS_PER_IMAGE =100 # Use a small epoch since the data is simple
STEPS_PER_EPOCH = 100 # use small validation steps since the epoch is small
VALIDATION_STEPS = 50 #import train_tongue
#class InferenceConfig(coco.CocoConfig):
class InferenceConfig(ShapesConfig):
# Set batch size to 1 since we'll be running inference on
# one image at a time. Batch size = GPU_COUNT * IMAGES_PER_GPU
GPU_COUNT = 1
IMAGES_PER_GPU = 1 config = InferenceConfig() model = modellib.MaskRCNN(mode="inference", model_dir=MODEL_DIR, config=config) # Create model object in inference mode.
model = modellib.MaskRCNN(mode="inference", model_dir=MODEL_DIR, config=config) # Load weights trained on MS-COCO
model.load_weights(COCO_MODEL_PATH, by_name=True) # COCO Class names
# Index of the class in the list is its ID. For example, to get ID of
# the teddy bear class, use: class_names.index('teddy bear')
class_names = ['BG', 'a','b','c','e']
# Load a random image from the images folder
file_names = next(os.walk(IMAGE_DIR))[2]
image = skimage.io.imread(os.path.join(IMAGE_DIR, random.choice(file_names))) a=datetime.now()
# Run detection
results = model.detect([image], verbose=1)
b=datetime.now()
# Visualize results
print("shijian",(b-a).seconds)
r = results[0]
visualize.display_instances(image, r['rois'], r['masks'], r['class_ids'],
class_names, r['scores'])
# Load a random image from the images folder
#file_names = next(os.walk(IMAGE_DIR))[2]
#image = skimage.io.imread(os.path.join(IMAGE_DIR, random.choice(file_names)))
#cap = cv2.VideoCapture(0)
#
#while(1):
# # get a frame
# ret, frame = cap.read()
# # show a frame
# start =time.clock()
# results = model.detect([frame], verbose=1)
# r = results[0]
# #cv2.imshow("capture", frame)
# visualize.display_instances(frame, r['rois'], r['masks'], r['class_ids'],
# class_names, r['scores'])
# end = time.clock()
# print(end-start)
# if cv2.waitKey(1) & 0xFF == ord('q'):
# break
#
#cap.release()
#cv2.destroyAllWindows() #image= cv2.imread("C:\\Users\\18301\\Desktop\\Mask_RCNN-master\\images\\9.jpg")
## Run detection
#
#results = model.detect([image], verbose=1)
#
#print(end-start)
## Visualize results
#r = results[0]
#visualize.display_instances(image, r['rois'], r['masks'], r['class_ids'],
# class_names, r['scores']) ## Root directory of the project
#ROOT_DIR = os.getcwd()
#
## Directory to save logs and trained model
#MODEL_DIR = os.path.join(ROOT_DIR, "logs/shapes20180713T1554")
#
## Local path to trained weights file
#COCO_MODEL_PATH = os.path.join(ROOT_DIR, "mask_rcnn_coco.h5")
## Download COCO trained weights from Releases if needed
#if not os.path.exists(COCO_MODEL_PATH):
# utils.download_trained_weights(COCO_MODEL_PATH)
#
## Directory of images to run detection on
#IMAGE_DIR = os.path.join(ROOT_DIR, "images")
#
#class ShapesConfig(Config):
# """Configuration for training on the toy shapes dataset.
# Derives from the base Config class and overrides values specific
# to the toy shapes dataset.
# """
# # Give the configuration a recognizable name
# NAME = "shapes"
#
# # Train on 1 GPU and 8 images per GPU. We can put multiple images on each
# # GPU because the images are small. Batch size is 8 (GPUs * images/GPU).
# GPU_COUNT = 1
# IMAGES_PER_GPU = 1
#
# # Number of classes (including background)
# NUM_CLASSES = 1 + 1 # background + 3 shapes
#
# # Use small images for faster training. Set the limits of the small side
# # the large side, and that determines the image shape.
# IMAGE_MIN_DIM = 320
# IMAGE_MAX_DIM = 384
#
# # Use smaller anchors because our image and objects are small
# RPN_ANCHOR_SCALES = (8 * 6, 16 * 6, 32 * 6, 64 * 6, 128 * 6) # anchor side in pixels
#
# # Reduce training ROIs per image because the images are small and have
# # few objects. Aim to allow ROI sampling to pick 33% positive ROIs.
# TRAIN_ROIS_PER_IMAGE =100
#
# # Use a small epoch since the data is simple
# STEPS_PER_EPOCH = 100
#
# # use small validation steps since the epoch is small
# VALIDATION_STEPS = 50
#
##import train_tongue
##class InferenceConfig(coco.CocoConfig):
#class InferenceConfig(ShapesConfig):
# # Set batch size to 1 since we'll be running inference on
# # one image at a time. Batch size = GPU_COUNT * IMAGES_PER_GPU
# GPU_COUNT = 1
# IMAGES_PER_GPU = 1
#
#config = InferenceConfig()
#
#model = modellib.MaskRCNN(mode="inference", model_dir=MODEL_DIR, config=config)
#
## Load weights trained on MS-COCO
## model.load_weights(COCO_MODEL_PATH, by_name=True)
#model_path = model.find_last()[0]
#
## Load trained weights (fill in path to trained weights here)
#assert model_path != "", "Provide path to trained weights"
#print("Loading weights from ", model_path)
#model.load_weights(model_path, by_name=True)
#
#class_names = ['BG', 'tank']
#
## Load a random image from the images folder
#file_names = next(os.walk(IMAGE_DIR))[2]
#image = skimage.io.imread(os.path.join(IMAGE_DIR, random.choice(file_names)))
#
## Run detection
#results = model.detect([image], verbose=1)
#
## Visualize results
#r = results[0]
#visualize.display_instances(image, r['rois'], r['masks'], r['class_ids'],
# class_names, r['scores'])

修改代码中的路径及数据集即可正常训练出自己的数据集

mask_rcnn训练自己的数据集的更多相关文章

  1. 【Tensorflow系列】使用Inception_resnet_v2训练自己的数据集并用Tensorboard监控

    [写在前面] 用Tensorflow(TF)已实现好的卷积神经网络(CNN)模型来训练自己的数据集,验证目前较成熟模型在不同数据集上的准确度,如Inception_V3, VGG16,Inceptio ...

  2. 目标检测算法SSD之训练自己的数据集

    目标检测算法SSD之训练自己的数据集 prerequesties 预备知识/前提条件 下载和配置了最新SSD代码 git clone https://github.com/weiliu89/caffe ...

  3. 可变卷积Deforable ConvNet 迁移训练自己的数据集 MXNet框架 GPU版

    [引言] 最近在用可变卷积的rfcn 模型迁移训练自己的数据集, MSRA官方使用的MXNet框架 环境搭建及配置:http://www.cnblogs.com/andre-ma/p/8867031. ...

  4. caffe训练自己的数据集

    默认caffe已经编译好了,并且编译好了pycaffe 1 数据准备 首先准备训练和测试数据集,这里准备两类数据,分别放在文件夹0和文件夹1中(之所以使用0和1命名数据类别,是因为方便标注数据类别,直 ...

  5. 使用yolo3模型训练自己的数据集

    使用yolo3模型训练自己的数据集 本项目地址:https://github.com/Cw-zero/Retrain-yolo3 一.运行环境 1. Ubuntu16.04. 2. TensorFlo ...

  6. Win10中用yolov3训练自己的数据集全过程(VS、CUDA、CUDNN、OpenCV配置,训练和测试)

    在Windows系统的Linux系统中用yolo训练自己的数据集的配置差异很大,今天总结在win10中配置yolo并进行训练和测试的全过程. 提纲: 1.下载适用于Windows的darknet 2. ...

  7. TensorFlow学习笔记——LeNet-5(训练自己的数据集)

    在之前的TensorFlow学习笔记——图像识别与卷积神经网络(链接:请点击我)中了解了一下经典的卷积神经网络模型LeNet模型.那其实之前学习了别人的代码实现了LeNet网络对MNIST数据集的训练 ...

  8. YOLO训练自己的数据集的一些心得

    YOLO训练自己的数据集 YOLO-darknet训练自己的数据 [Darknet][yolo v2]训练自己数据集的一些心得----VOC格式 YOLO模型训练可视化训练过程中的中间参数 项目开源代 ...

  9. YOLO V3训练自己的数据集

    数据的输入几乎和Faster rcnn一样,标签格式xml是一样的. 相比Faster rcnn,数据多了一步处理,通过voc_annotation.py将图片路径和bbox+class存储在txt下 ...

随机推荐

  1. freeswitch 事件命令

    1.uuid_bridge 桥接两条呼叫的腿. Usage: uuid_bridge <uuid> <other_uuid> uuid_bridge至少需要有一条腿是被呼通的. ...

  2. C# 启动外部进程

    C# 启动外部进程: var processInfo = new ProcessStartInfo(fullName); processInfo.UseShellExecute = false; pr ...

  3. CF 528D. Fuzzy Search NTT

    CF 528D. Fuzzy Search NTT 题目大意 给出文本串S和模式串T和k,S,T为DNA序列(只含ATGC).对于S中的每个位置\(i\),只要中[i-k,i+k]有一个位置匹配了字符 ...

  4. 论文笔记:Fast Online Object Tracking and Segmentation: A Unifying Approach

    Fast Online Object Tracking and Segmentation: A Unifying Approach CVPR-2019 2019-03-11 23:45:12 Pape ...

  5. 殊途同归 - Church-Rosser and Consistency of Evaluation

        在"解释语言的语言"中提到,设计一个新的语言,仅仅是使用meta-language给出其描述是不够的,我们还需要去验证一些性质.     考虑一下我们在"解释语言 ...

  6. 6、Docker存储卷

    Why Data Volumes?  来自马哥教育 Data volumes Volume types  绑定挂载卷:在宿主机和容器上各指明绑定路径才能进行绑定. docker管理卷:在容器内指定挂载 ...

  7. Luogu P1245 电话号码

    Luogu P1245 电话号码 谨以此题解致敬我的初中英语老师孙菡老师,她带的班默写不过的人数总是像电话号码那样屈指可数 玄学问题? 本题的SPJ似乎已经基本没有问题了,只要 文末没有多余的空格和回 ...

  8. 爬虫基础之requests模块

    1. 爬虫简介 1.1 概述 网络爬虫(又被称为网页蜘蛛,网络机器人,在FOAF社区中间,更经常的称为网页追逐者),是一种按照一定的规则,自动地抓取万维网信息的程序或者脚本. 1.2 爬虫的价值 在互 ...

  9. [原][译]我们为什么需要另一个c++测试框架?Catch||Why do we need yet another C++ test framework?

    翻译问题来源:https://github.com/catchorg/Catch2/blob/master/docs/why-catch.md 其他辅助博文:从Google Test 转到 Catch ...

  10. 如何快速连接无线Wifi 使用二维码

    无线Wifi现在已经很普及了,无论是在家.还是在单位.书店.餐馆.咖啡馆等公共场所,只要手机打开Wifi,选择相应的无线Wifi热点,手工输入密码后,即可通过无线Wifi访问互联网. 如何让用户更方便 ...