当前位置: 首页 > 编程日记 > 正文

Caffe源码中io文件分析

Caffe源码(caffe version commit: 09868ac , date: 2015.08.15)中有一些重要的头文件,这里介绍下include/caffe/util/io.hpp文件的内容:

1.      include文件:

(1)、<google/protobuf/message.h>:关于protobuf的介绍可以参考:http://blog.csdn.net/fengbingchun/article/details/49977903

(2)、<caffe/blob.hpp>:此文件的介绍可以参考:http://blog.csdn.net/fengbingchun/article/details/59106613

(3)、<caffe/common.hpp>:此文件的介绍可以参考:http://blog.csdn.net/fengbingchun/article/details/54955236

(4)、<caffe/proto/caffe.pb.h>:此文件的介绍可以参考:http://blog.csdn.net/fengbingchun/article/details/55267162

2.      <mkstemp.h>文件:

此文件是来自于libc/sysdeps/posix/tempname.c,此文件中包含一个静态全局常量letters和一个基于TMPL生成临时文件名的函数mkstemp。此文件在源码中没有用到,仅在test文件中用到。此文件仅在Linux下使用,在Windows下直接使用会有问题,而且在新版的Caffe中,已将此文件移除。

3.      函数:

此文件中的函数主要作用包括:读取prototxt文本文件并解析(反序列化);生成prototxt文本文件即序列化;读取caffemodel二进制文件并解析(反序列化);生成caffemodel二进制文件即序列化;读取二进制文件、图像文件到Datum类;对Datum进行解码;将图像读取到cv::Mat;解码Datum到cv::Mat;将cv::Mat转换为Datum。

Datum既可以直接存储解码前的数据,也可以存储解码后的数据。Datum支持两种数据类型string和float。

<caffe/util/io.hpp>文件的详细介绍如下:

#ifndef CAFFE_UTIL_IO_H_
#define CAFFE_UTIL_IO_H_#include <unistd.h>
#include <string>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>#include "google/protobuf/message.h"#include "caffe/blob.hpp"
#include "caffe/common.hpp"
#include "caffe/proto/caffe.pb.h"#include "mkstemp.h"namespace caffe {using ::google::protobuf::Message;// 生成临时文件,在windows下不能直接调用此文件
// 此函数在新版的Caffe中,在windows下可以直接调用
inline void MakeTempFilename(string* temp_filename) {temp_filename->clear();*temp_filename = "/tmp/caffe_test.XXXXXX";char* temp_filename_cstr = new char[temp_filename->size() + 1];// NOLINT_NEXT_LINE(runtime/printf)strcpy(temp_filename_cstr, temp_filename->c_str());int fd = mkstemp(temp_filename_cstr);CHECK_GE(fd, 0) << "Failed to open a temporary file at: " << *temp_filename;
#ifndef _MSC_VERclose(fd);
#else_close(fd);
#endif*temp_filename = temp_filename_cstr;delete[] temp_filename_cstr;
}// 生成临时目录,在windows下不能直接调用此文件
// 此函数在新版的Caffe中,在windows下可以直接调用
inline void MakeTempDir(string* temp_dirname) {temp_dirname->clear();*temp_dirname = "/tmp/caffe_test.XXXXXX";char* temp_dirname_cstr = new char[temp_dirname->size() + 1];// NOLINT_NEXT_LINE(runtime/printf)strcpy(temp_dirname_cstr, temp_dirname->c_str());//char* mkdtemp_result = mkdtemp(temp_dirname_cstr);
#ifndef _MSC_VER char* mkdtemp_result = mkdtemp(temp_dirname_cstr);
#elseerrno_t mkdtemp_result = _mktemp_s(temp_dirname_cstr, sizeof(temp_dirname_cstr));
#endifCHECK(mkdtemp_result != NULL)<< "Failed to create a temporary directory at: " << *temp_dirname;*temp_dirname = temp_dirname_cstr;delete[] temp_dirname_cstr;
}// 读取prototxt文本文件并解析(反序列化)
bool ReadProtoFromTextFile(const char* filename, Message* proto);
// 读取prototxt文本文件并解析(反序列化)
inline bool ReadProtoFromTextFile(const string& filename, Message* proto) {return ReadProtoFromTextFile(filename.c_str(), proto);
}
// 读取prototxt文本文件并解析(反序列化)
inline void ReadProtoFromTextFileOrDie(const char* filename, Message* proto) {CHECK(ReadProtoFromTextFile(filename, proto));
}
// 读取prototxt文本文件并解析(反序列化)
inline void ReadProtoFromTextFileOrDie(const string& filename, Message* proto) {ReadProtoFromTextFileOrDie(filename.c_str(), proto);
}// 生成prototxt文本文件,即序列化
void WriteProtoToTextFile(const Message& proto, const char* filename);
// 生成prototxt文本文件,即序列化
inline void WriteProtoToTextFile(const Message& proto, const string& filename) {WriteProtoToTextFile(proto, filename.c_str());
}// 读取caffemodel二进制文件并解析(反序列化)
bool ReadProtoFromBinaryFile(const char* filename, Message* proto);
// 读取caffemodel二进制文件并解析(反序列化)
inline bool ReadProtoFromBinaryFile(const string& filename, Message* proto) {return ReadProtoFromBinaryFile(filename.c_str(), proto);
}
// 读取caffemodel二进制文件并解析(反序列化)
inline void ReadProtoFromBinaryFileOrDie(const char* filename, Message* proto) {CHECK(ReadProtoFromBinaryFile(filename, proto));
}
// 读取caffemodel二进制文件并解析(反序列化)
inline void ReadProtoFromBinaryFileOrDie(const string& filename, Message* proto) {ReadProtoFromBinaryFileOrDie(filename.c_str(), proto);
}// 生成caffemodel二进制文件,即序列化
void WriteProtoToBinaryFile(const Message& proto, const char* filename);
// 生成caffemodel二进制文件,即序列化
inline void WriteProtoToBinaryFile(const Message& proto, const string& filename) {WriteProtoToBinaryFile(proto, filename.c_str());
}// 注:以下的Datum是定义在caffe.proto中的一个message,其字段有channels、height、width、data、label、float_data、encoded
// 读取二进制数据文件到Datum类
bool ReadFileToDatum(const string& filename, const int label, Datum* datum);
// 读取二进制数据文件到Datum类
inline bool ReadFileToDatum(const string& filename, Datum* datum) {return ReadFileToDatum(filename, -1, datum);
}// 读取图像文件到Datum类
bool ReadImageToDatum(const string& filename, const int label,const int height, const int width, const bool is_color,const std::string & encoding, Datum* datum);
// 读取图像文件到Datum类
inline bool ReadImageToDatum(const string& filename, const int label,const int height, const int width, const bool is_color, Datum* datum) {return ReadImageToDatum(filename, label, height, width, is_color,"", datum);
}
// 读取图像文件到Datum类
inline bool ReadImageToDatum(const string& filename, const int label,const int height, const int width, Datum* datum) {return ReadImageToDatum(filename, label, height, width, true, datum);
}
// 读取图像文件到Datum类
inline bool ReadImageToDatum(const string& filename, const int label,const bool is_color, Datum* datum) {return ReadImageToDatum(filename, label, 0, 0, is_color, datum);
}
// 读取图像文件到Datum类
inline bool ReadImageToDatum(const string& filename, const int label, Datum* datum) {return ReadImageToDatum(filename, label, 0, 0, true, datum);
}
// 读取图像文件到Datum类
inline bool ReadImageToDatum(const string& filename, const int label,const std::string & encoding, Datum* datum) {return ReadImageToDatum(filename, label, 0, 0, true, encoding, datum);
}// 对Datum进行解码
bool DecodeDatumNative(Datum* datum);
// 对Datum进行解码
bool DecodeDatum(Datum* datum, bool is_color);// 将图像读取到cv::Mat(可选择读取灰度图还是彩色图、可进行图像缩放操作)
cv::Mat ReadImageToCVMat(const string& filename,const int height, const int width, const bool is_color);
// 将图像读取到cv::Mat
cv::Mat ReadImageToCVMat(const string& filename,const int height, const int width);
// 将图像读取到cv::Mat
cv::Mat ReadImageToCVMat(const string& filename,const bool is_color);
// 将图像读取到cv::Mat
cv::Mat ReadImageToCVMat(const string& filename);// 解码Datum到cv::Mat
cv::Mat DecodeDatumToCVMatNative(const Datum& datum);
// 解码Datum到cv::Mat
cv::Mat DecodeDatumToCVMat(const Datum& datum, bool is_color);// 将cv::Mat转换为Datum
void CVMatToDatum(const cv::Mat& cv_img, Datum* datum);}  // namespace caffe#endif   // CAFFE_UTIL_IO_H_
在caffe.proto文件中,有一个message是与io相关的,如下:

message Datum { // 存储图像数据,可以解码前的即编码,也可以是解码后的optional int32 channels = 1; // 图像通道数optional int32 height = 2; // 图像高optional int32 width = 3; // 图像宽// the actual image data, in bytesoptional bytes data = 4; // 以std::string类型存储图像数据optional int32 label = 5; // 当前图像对应的label值// Optionally, the datum could also hold float data.repeated float float_data = 6; // 以float类型存储图像数据// If true data contains an encoded image that need to be decodedoptional bool encoded = 7 [default = false]; // 是否是编码数据
}
io的测试代码如下:

#include "funset.hpp"
#include <string>
#include <vector>
#include "common.hpp"static bool ReadImageToDatumReference(const std::string& filename, const int label,const int height, const int width, const bool is_color, caffe::Datum* datum)
{cv::Mat cv_img;int cv_read_flag = (is_color ? CV_LOAD_IMAGE_COLOR : CV_LOAD_IMAGE_GRAYSCALE);cv::Mat cv_img_origin = cv::imread(filename, cv_read_flag);if (!cv_img_origin.data) {fprintf(stderr, "Could not open or find file: %s\n", filename.c_str());return false;}if (height > 0 && width > 0)cv::resize(cv_img_origin, cv_img, cv::Size(width, height));elsecv_img = cv_img_origin;int num_channels = (is_color ? 3 : 1);datum->set_channels(num_channels);datum->set_height(cv_img.rows);datum->set_width(cv_img.cols);datum->set_label(label);datum->clear_data();datum->clear_float_data();std::string* datum_string = datum->mutable_data();if (is_color) {for (int c = 0; c < num_channels; ++c) {for (int h = 0; h < cv_img.rows; ++h) {for (int w = 0; w < cv_img.cols; ++w) {datum_string->push_back(static_cast<char>(cv_img.at<cv::Vec3b>(h, w)[c]));}}}} else {  // Faster than repeatedly testing is_color for each pixel w/i loopfor (int h = 0; h < cv_img.rows; ++h) {for (int w = 0; w < cv_img.cols; ++w) {datum_string->push_back(static_cast<char>(cv_img.at<uchar>(h, w)));}}}return true;
}static int CompareDatumMat(const caffe::Datum& datum1, const caffe::Datum& datum2)
{if (datum1.channels() != datum2.channels() || datum1.height() != datum2.height() ||datum1.width() != datum2.width() || datum1.data().size() != datum2.data().size()) {fprintf(stderr, "these values should be equal\n");return -1;}const std::string& data1 = datum1.data();const std::string& data2 = datum2.data();for (int i = 0; i < datum1.data().size(); ++i) {if (data1[i] != data2[i]) {fprintf(stderr, "their data should be equal\n");return -1;}}return 0;
}static int CompareDatumMat(const caffe::Datum& datum, const cv::Mat& mat)
{if (datum.channels() != mat.channels() || datum.height() != mat.rows || datum.width() != mat.cols) {fprintf(stderr, "these values should be equal\n");return -1;}const std::string& datum_data = datum.data();int index = 0;for (int c = 0; c < mat.channels(); ++c) {for (int h = 0; h < mat.rows; ++h) {for (int w = 0; w < mat.cols; ++w) {if (datum_data[index++] != static_cast<char>(mat.at<cv::Vec3b>(h, w)[c])) {fprintf(stderr, "their data should be equal\n");return -1;}}}}return 0;
}static int CompareDatumMat(const cv::Mat& mat1, const cv::Mat& mat2)
{if (mat1.channels() != mat2.channels() || mat1.rows != mat2.rows || mat1.cols != mat2.cols) {fprintf(stderr, "these values should be equal\n");return -1;}for (int c = 0; c < mat1.channels(); ++c) {for (int h = 0; h < mat1.rows; ++h) {for (int w = 0; w < mat1.cols; ++w) {if (mat1.at<cv::Vec3b>(h, w)[c] != mat2.at<cv::Vec3b>(h, w)[c]) {fprintf(stderr, "their data should be equal\n");return -1;}}}}return 0;
}int test_caffe_util_io()
{std::string filename{ "E:/GitCode/Caffe_Test/test_data/images/a.jpg" };// 1. caffe::ReadImageToDatumcaffe::Datum datum1;caffe::ReadImageToDatum(filename, 0, &datum1);fprintf(stderr, "datum1: channels: %d, height: %d, width: %d\n",datum1.channels(), datum1.height(), datum1.width());// 2. test ReadImageToDatumReferencecaffe::Datum datum2, datum_ref2;caffe::ReadImageToDatum(filename, 0, 0, 0, true, &datum2);ReadImageToDatumReference(filename, 0, 0, 0, true, &datum_ref2);if(CompareDatumMat(datum2, datum_ref2) != 0) return -1;// 3. test ReadImageToDatumReferenceResizedcaffe::Datum datum3, datum_ref3;caffe::ReadImageToDatum(filename, 0, 100, 200, true, &datum3);ReadImageToDatumReference(filename, 0, 100, 200, true, &datum_ref3);if (CompareDatumMat(datum3, datum_ref3) != 0) return -1;// 4. test ReadImageToDatumContentcaffe::Datum datum4;caffe::ReadImageToDatum(filename, 0, &datum4);cv::Mat cv_img = caffe::ReadImageToCVMat(filename);if (CompareDatumMat(datum4, cv_img) != 0) return -1;// 5. test CVMatToDatumContentcv_img = caffe::ReadImageToCVMat(filename);caffe::Datum datum5;caffe::CVMatToDatum(cv_img, &datum5);caffe::Datum datum_ref5;caffe::ReadImageToDatum(filename, 0, &datum_ref5);if (CompareDatumMat(datum5, datum_ref5) != 0) return -1;// 6. test ReadFileToDatumcaffe::Datum datum6;if (!caffe::ReadFileToDatum(filename, &datum6)) {fprintf(stderr, "read file to datum fail\n");return -1;}fprintf(stderr, "datum encoded: %d; datum label: %d, datum size: %d\n",datum6.encoded(), datum6.label(), datum6.data().size());// 7. test DecodeDatumcaffe::Datum datum7;caffe::ReadFileToDatum(filename, &datum7);if (!caffe::DecodeDatum(&datum7, true)) return -1;if(caffe::DecodeDatum(&datum7, true)) return -1;caffe::Datum datum_ref7;ReadImageToDatumReference(filename, 0, 0, 0, true, &datum_ref7);if (CompareDatumMat(datum7, datum_ref7) != 0) return -1;// 8. test DecodeDatumToCVMatContentcaffe::Datum datum8;if (!caffe::ReadImageToDatum(filename, 0, std::string("jpg"), &datum8)) return -1;cv::Mat cv_img8 = caffe::DecodeDatumToCVMat(datum8, true);cv::Mat cv_img_ref = caffe::ReadImageToCVMat(filename);// if (CompareDatumMat(cv_img8, cv_img_ref) != 0) return -1; // Note: some values are not equal// 9. read prototxt and parsestd::string solver_prototxt{ "E:/GitCode/Caffe_Test/test_data/model/mnist/lenet_solver.prototxt" };caffe::SolverParameter solver_param;if (!caffe::ReadProtoFromTextFile(solver_prototxt.c_str(), &solver_param)) {fprintf(stderr, "parse solver.prototxt fail\n");return -1;}// 10. write prototxt to text filestd::string save_prototxt{"E:/GitCode/Caffe_Test/test_data/test.prototxt"};caffe::WriteProtoToTextFile(solver_param, save_prototxt);return 0;
}
测试结果如下:

生成的test.prototxt文件结果如下:


GitHub:https://github.com/fengbingchun/Caffe_Test

相关文章:

DeepMind悄咪咪开源三大新框架,深度强化学习落地希望再现

作者 | Jesus Rodriguez译者 | 夕颜出品 | AI科技大本营&#xff08;ID:rgznai100&#xff09;【导读】近几年&#xff0c;深度强化学习&#xff08;DRL&#xff09;一直是人工智能取得最大突破的核心。尽管取得了很多进展&#xff0c;但由于缺乏工具和库&#xff0c;DRL 方法仍…

seq2seq

链接&#xff1a; https://blog.csdn.net/wuzqchom/article/details/75792501 转载于:https://www.cnblogs.com/yttas/p/10631442.html

vip能ping通,但80不通的解决方法

最近遇到一个很奇怪的问题&#xff0c;在做两台服务器负载均衡的时候&#xff0c;vip已经添加了&#xff0c;而且能ping通了&#xff0c;但是页面访问不了&#xff0c;也就是说80端口一直不通&#xff0c;ipvsadm -lnc查看链接状态全部是SYN_RECV。网上找了好长时间&#xff0c…

OpenCV中imread/imwrite与imdecode/imencode的异同

OpenCV中的cv::imdecode函数是从指定的内存缓存中读一幅图像&#xff0c;而cv::imencode是将一幅图像写进内存缓存中。cv::imread是从指定文件载入一幅图像&#xff0c;cv::imwrite是保存一幅图像到指定的文件中。cv::imread和cv::imdecode内部都是通过ImageDecoder类来进行图像…

奖金+招聘绿色通道,这一届算法大赛关注下?

大赛背景伴随着5G、物联网与大数据形成的后互联网格局的逐步形成&#xff0c;日益多样化的用户触点、庞杂的行为数据和沉重的业务体量也给我们的数据资产管理带来了不容忽视的挑战。为了建立更加精准的数据挖掘形式和更加智能的机器学习算法&#xff0c;对不断生成的用户行为事…

Linux文件属性

文件属性和权限 [rootdaf root]# ls -al total 64 drwxr-x--- 4 root root 4096 Feb 14 22:02 . drwxr-xr-x 23 root root 4096 Feb 16 13:35 .. -rw-r--r-- 1 root root 1210 Feb 10 06:03 anaconda-ks.cfg -rw------- 1…

Caffe源码中layer文件分析

Caffe源码(caffe version commit: 09868ac , date: 2015.08.15)中有一些重要的头文件&#xff0c;这里介绍下include/caffe/layer.hpp文件的内容&#xff1a;1. include文件&#xff1a;(1)、<caffe/blob.hpp>&#xff1a;此文件的介绍可以参考&#xff1a;http://b…

全球首个软硬件推理平台 :NVDLA编译器正式开源

作者 | 神经小姐姐来源 | HyperAI超神经&#xff08;ID:HyperAI&#xff09;【导读】为深度学习设计新的定制硬件加速器&#xff0c;是目前的一个趋势&#xff0c;但用一种新的设计&#xff0c;实现最先进的性能和效率却具有挑战性。近日&#xff0c;英伟达开源了软硬件推理平台…

【leetcode】1018. Binary Prefix Divisible By 5

题目如下&#xff1a; Given an array A of 0s and 1s, consider N_i: the i-th subarray from A[0] to A[i] interpreted as a binary number (from most-significant-bit to least-significant-bit.) Return a list of booleans answer, where answer[i]is true if and only …

php中magic_quotes_gpc对unserialize的影响

昨天朋友让我帮他解决下他网站的购物车程序的问题&#xff0c;程序用的是PHPCMS&#xff0c;换空间前是好的&#xff08;刚换的空间&#xff09;&#xff0c;具体问题是提示成功加入购物车后跳转到购物车页面&#xff0c;购物车里为空。 我看了下代码&#xff0c;大致的原理就是…

值得收藏!基于激光雷达数据的深度学习目标检测方法大合集(上)

作者 | 黄浴转载自知乎专栏自动驾驶的挑战和发展【导读】上周&#xff0c;我们在激光雷达&#xff0c;马斯克看不上&#xff0c;却又无可替代&#xff1f;》一文中对自动驾驶中广泛使用的激光雷达进行了简单的科普&#xff0c;今天&#xff0c;这篇文章将各大公司和机构基于激光…

Caffe源码中Pooling Layer文件分析

Caffe源码(caffe version commit: 09868ac , date: 2015.08.15)中有一些重要的头文件&#xff0c;这里介绍下include/caffe/vision_layers文件中PoolingLayer类&#xff0c;在最新版caffe中&#xff0c;PoolingLayer类被单独放在了include/caffe/layers/pooling_layer.hpp文件中…

手持终端以物联网的模式

近年来&#xff0c;物联宇手持终端以物联网的模式&#xff0c;开启了信息化的管理模式&#xff0c;迸发了新的自我提升和业务新商机。手持终端是一款智能的电子设备&#xff0c;它的核心功能为用户速带来业务效率的提升&#xff0c;如快递行业&#xff0c;每天的工作量需求大&a…

Linux系统基础-管理之用户、权限管理

Linux用户、权限管理一、如何实现"用户管理"1.什么是用户 "User" : 是一个使用者获取系统资源的凭证&#xff0c;是权限的结合&#xff0c;为了识别界定每一个用户所能访问的资源及其服务的。只是一种凭证。会有一个表示数字&#xff0c;计算机会首…

Ubuntu14.04 LTS中安装Ruby 2.4源码操作步骤

(1)、查看是否已安装ruby&#xff0c;执行命令&#xff0c;如下图&#xff0c;可见机子上还没有安装ruby&#xff0c;即使通过apt-get install命令安装也只能安装1.8版本&#xff1b;(2)、从 http://www.ruby-lang.org/en/downloads/ 下载最新稳定版2.4即ruby-2.4.0.tar.gz&a…

图森未来完成2.15亿美元D轮融资,将拓展无人驾驶运输服务

AI科技大本营消息&#xff0c;9月17日&#xff0c;图森未来宣布获得1.2亿美元的D2轮投资&#xff0c;并完成总额为2.15亿美元的D轮融资。D2轮的投资方除了此前已宣布的UPS外&#xff0c;还包括新的投资方鼎晖资本&#xff0c;以及一级供应商万都&#xff08;Mando Corporation&…

中国互联网公司开源项目调研报告

近年来&#xff0c;开源技术得到越来越多的重视&#xff0c;微软收购GitHub、IBM收购红帽&#xff0c;都表明了开源的价值。国内公司也越来越多的参与开源&#xff0c;加入开源基金会/贡献开源项目。但是&#xff0c;它们到底做得如何呢&#xff1f;为此InfoQ统计了国内在GitHu…

ReSharper 配置及用法

1:安装后&#xff0c;Resharper会用他自己的英文智能提示&#xff0c;替换掉 vs2010的智能提示&#xff0c;所以我们要换回到vs2010的智能提示 2:快捷键。是使用vs2010的快捷键还是使用 Resharper的快捷键呢&#xff1f;我是使用re的快捷键 3: Resharper安装后&#xff0c;会做…

Ubuntu14.04 LTS中升级gcc/g++版本到4.9.4的操作步骤

Ubuntu14.04 LTS中默认的gcc/g版本为4.8.4&#xff0c;如下图&#xff0c;在C11中增加了对正则表达式的支持&#xff0c;但是好像到gcc/g 4.9.2版本才会对正则表达式能很好的支持&#xff0c;这里介绍下Ubuntu14.04 LTS升级gcc/g版本到4.9.4的操作步骤&#xff1a; 1&#xff0…

华为全球最快AI训练集群Atlas 900诞生

作者 | 胡巍巍来源 | CSDN&#xff08;ID&#xff1a;CSDNnews&#xff09;你&#xff0c;和计算有什么关系&#xff1f;早上&#xff0c;你打开手机App&#xff0c;查看天气预报&#xff0c;和计算有关&#xff1b;中午&#xff0c;你打开支付宝人脸支付&#xff0c;买了份宫保…

rabbitmq可靠发送的自动重试机制 --转

原贴地址 https://www.jianshu.com/p/6579e48d18ae https://www.jianshu.com/p/4112d78a8753 git项目代码地址 https://github.com/littlersmall/rabbitmq-access 转载于:https://www.cnblogs.com/hmpcly/p/10641688.html

在Linux下如何安装配置SVN服务

2019独角兽企业重金招聘Python工程师标准>>> Linux下在阿里云上架一个svn centos上安装&#xff1a;yum install subversion 安装成功 键入命令 svnserve --version 有版本信息则进行下一步 1、新建版本库目录 mkdir -p /opt/svndata/repos 2、设置此目录为…

201671030129 周婷 《英文文本统计分析》结对项目报告

项目内容这个作业属于哪个课程软件工程这个作业的要求在哪里软件工程结对项目课程学习目标熟悉软件开发整体流程及结对编程&#xff0c;提升自身能力本次作业在哪个具体方面帮助我们实现目标体验组队编程&#xff0c;体验一个完整的工程任务一&#xff1a; 作业所点评博客GetHu…

C++/C++11中std::string用法汇总

C/C11中std::string是个模板类&#xff0c;它是一个标准库。使用string类型必须首先包含<string>头文件。作为标准库的一部分&#xff0c;string定义在命名空间std中。std::string是C中的字符串。字符串对象是一种特殊类型的容器&#xff0c;专门设计来操作字符序列。str…

你在付费听《说好不哭》,我在这里免费看直播还送书 | CSDN新书发布会

周一的时候&#xff0c;我拖着疲惫的身体回到家中&#xff0c;躺倒床上刷刷朋友圈&#xff0c;什么&#xff1f;周杰伦出新歌了&#xff1f;朋友圈都是在分享周杰伦的新歌《说好不哭》&#xff0c;作为周杰伦的粉丝&#xff0c;我赶紧打开手机上的QQ音乐&#xff0c;准备去听&a…

解决Mysql:unrecognized service错误的方法(CentOS)附:修改用户名密码

2019独角兽企业重金招聘Python工程师标准>>> service mysql start出错&#xff0c;mysql启动不了&#xff0c;解决mysql: unrecognized service错误的方法如下&#xff1a; [rootctohome.com ~]# service mysql startmysql: unrecognized service [rootctohome.co…

Caffe源码中Net文件分析

Caffe源码(caffe version commit: 09868ac , date: 2015.08.15)中有一些重要的头文件&#xff0c;这里介绍下include/caffe/net.hpp文件的内容&#xff1a;1. include文件&#xff1a;(1)、<caffe/blob.hpp>&#xff1a;此文件的介绍可以参考&#xff1a;http://blo…

满满干货的硬核技术沙龙,免费看直播还送书 | CSDN新书发布会

周一的时候&#xff0c;我拖着疲惫的身体回到家中&#xff0c;躺倒床上刷刷朋友圈&#xff0c;什么&#xff0c;周杰伦出新歌了&#xff1f;朋友圈都是在分享周杰伦的新歌《说好的不哭》&#xff0c;作为周杰伦的粉丝&#xff0c;我赶紧打开我手机上的QQ音乐&#xff0c;准备去…

【重磅上线】思维导图工具XMind:ZEN基础问题详解合集

XMind是XMind Ltd公司旗下一款出色的思维导图和头脑风暴软件。黑暗的UI设计、独特的ZEN模式、丰富的风格和主题、多分支的颜色等等功能会让你的工作更加便捷与高效。在视觉感官上也会给你带来最佳的体验感。 对于初学者来说&#xff0c;肯定会遇到各种各样的问题&#xff0c;有…

Linux内置的审计跟踪工具:last命令

这个命令是last。它对于追踪非常有用。让我们来看一下last可以为你做些什么。last命令的功能是什么last显示的是自/var/log/wtmp文件创建起所有登录(和登出)的用户。这个文件是二进制文件&#xff0c;它不能被文本编辑器浏览&#xff0c;比如vi、Joe或者其他软件。这是非常有用…