OpenCV可移植图形工具HighGUI实现图像和视频操作

OpenCV把用于操作系统、文件系统以及摄像机等硬件设备交换的函数纳入了HighGUI(High-level Graphical User Interface)模块中。有了HighGUI模块,我们可以方便地打开窗口、显示图像、读出或写入图像相关的文件、鼠标事件和键盘事件。下面将对三部分分别进行介绍。

HighGUI三部分的作用
部分作用
硬件部分最主要是对摄像机的操作
文件系统部分主要工作是完成图片的载入和保存
窗口系统GUI创建窗口并将图片放入窗口显示,同时添加响应鼠标和键盘事件功能

图像文件的处理

图像的载入与保存

使用cv::imread()读取图片

cv::Mat cv::imread(const string& filename, int flags=cv::IMREAD_COLOR)

作用:载入图像,若失败不会抛出异常,返回的是空的cv::Mat(可以用cv::Mat::empty()==true来判断)。

flags的取值
标志含义默认值
cv::IMREAD_COLOR读取三通道图像,即使输入是灰度图像,也会有三通道,只是每个通道拥有相同的数据
cv::IMREAD_GRAYSCALE读取单通道图像
cv::IMREAD_ANYCOLOR通道数由文件实际通道数(不超过3)
cv::IMREAD_ANYDEPTH允许加载超过8bit深度
cv::IMREAD_UNCHANGED相当于cv::IMREAD_ANYCOLOR和cv::IMREAD_ANYDEPTH组合使用,可保留alpha通道。

使用cv::imwrite()保存图像

bool cv::imwrite(const string& filename, InputArray image, const vector<int>& params=vector<int>())

作用:保存图像,成功返回true,否则返回false。

常用扩展名
扩展名格式大小通道
.jpg或.jpegbaseline JPEG8位单通道或三通道
.jp2JPEG20008位或16位单通道或三通道
.tif或.tiffTIFF8位或16位单通道、三通道或四通道
.pngPNG8位或16位单通道、三通道或四通道
.bmpBMP8位单通道、三通道或四通道
.ppm或.pgmNetPBM8位单通道(PGM)和三通道(PPM)
params的使用
标志含义取值范围默认值
cv::IMWRITE_JPG_QUALITYJPEG的质量0~10095
cv::IMWRITE_PNG_COMPRESSIONPNG压缩值0~93
cv::IMWRITE_PXM_BINARY对PPM、PGM或PBM文件是否使用二值格式0或11

关于codecs的一些注释

用于图像处理的库通常被叫做codecs(co-mpression and dec-compress libraries-s)。OpenCV对一些图片格式自带编码解码库,对于这些有一下三中选择:

① 不使用这些编码解码库;

② 使用OpenCV所提供的编码解码库;

③ 使用相应的拓展库(如libjpeg、libpng等)。

在Windows系统中默认选②选项,而在OS X或Linux系统上,默认选③选项。

图片的编码与解码

使用cv::imencode()压缩图像

void cv::imencode(const string& ext, InputArray img, vector<uchar>& buf, const vector<int>& params=vector<int>())

作用:对图像进行编码。

参数列表
参数含义
ext文件扩展名,用于函数与对应的编码压缩方式相关联。指明格式并帮助系统索引对应编码库
img要被压缩的图像数据
buf用来存储编码压缩后的图像数据的字符数组
params指明要使用编码器的输入参数

使用cv::imdecode()解码文件

cv::Mat cv::imdecode(InputArray buf, int flags=cv::IMREAD_COLOR)

作用:将字节流数据解码成数组形式的图像。

视频处理

使用cv::VideoCapture对象读取视频流

cv::VideoCapture::VideoCapture(const string& filename)

cv::VideoCapture::VideoCapture(int device)

cv::VideoCapture::VideoCapture()

作用:打开视频文件或摄像机。打开成功则cv::VideoCapture::isOpen()会返回true,否则返回false。

构造设备参数时,传入的标识符是相机的域索引和相机索引之和。相机索引是指系统中摄像机设备的索引,从0开始计数。相机域表明我们用何种相机,如下表所示。

相机域常量
相机捕捉常数数值相机捕捉常数数值相机捕捉常数数值
cv::CAP_ANY0cv::CAP_DSHOW700cv::CAP_OPENNI21600
cv::CAP_MIL100cv::CAP_PVAPI800cv::CAP_OPENNI2_ASUS1610
cv::CAP_VFW200cv::CAP_OPENNI900cv::CAP_GPHOTO21700
cv::CAP_V4L200cv::CAP_OPENNI_ASUS910cv::CAP_GSTREAMER1800
cv::CAP_V4L2200cv::CAP_ANDROID1000cv::CAP_FFMPEG1900
cv::CAP_FIREWIRE300cv::CAP_XIAPI1100cv::CAP_IMAGES2000
cv::CAP_FIREWARE300cv::CAP_AVFOUNDATION1200cv::CAP_ARAVIS2100
cv::CAP_IEEE11394300cv::CAP_GIGANETIX1300cv::CAP_OPENCV_MJPEG2200
cv::CAP_DC1394300cv::CAP_MSMF1400cv::CAP_INTEL_MFX2300
cv::CAP_QT500cv::CAP_WINRT1410cv::CAP_XINE2400
cv::CAP_UNICAP600cv::CAP_INTELPERC1500  

当传入的标识符为-1时,则OpenCV会弹出一个选择窗口,可手动选择希望使用的相机。

最后一种形式只是直接创建一个VideoCapture对象,无法直接使用,需要调用cv::VideoCapture::open()函数来指定文件名或设备号,和前两种形式一样。

使用cv::VideoCapture::read()从视频流中读取图像

bool cv::VideoCapture::read(OutputArray img)

作用:从文件中读取下一帧数据,并将结果存入img中,并会自动更新。读取成功返回true,读取失败返回false。

使用cv::VideoCapture::operator>>()从视频流读取图像数据

cv::VideoCapture& cv::VideoCapture::operator>>(Mat& img)

作用:重载输入流操作符,从文件中读取下一帧数据,并将结果存入img中。

使用cv::VideoCapture::grab()和cv::VideoCapture::retrieve()从视频流中读取图像数据

bool cv::VideoCapture::grab()

作用:将当前可使用的图像数据拷贝至用户看不到的一个内存缓存区。抓取的图像帧是未处理的,该函数只是设计用于将原始数据尽快获取到电脑。

bool cv::VideoCapture::retrieve(OutputArray image, int channel)

作用:对内部缓存数据进行必要的图像解码、内存分配与拷贝,最后以Mat形式的序列将图像帧返回。

相机属性cv::VideoCapture::get()和cv::VideoCapture::set()

double cv::VideoCapture::get(int propid)

bool cv::VideoCapture::set(int propid, double value)

作用:获取或设置元数据(meta data)。

视频捕捉属性常量
ID是否只在摄像头模式下可以使用含义
cv::CAP_PROP_POS_MSEC 视频文件中当前位置(毫秒)或视频捕获时间戳
cv::CAP_PROP_POS_FRAMES 从0开始下一帧的索引
cv::CAP_PROP_POS_AVI_RATIO 视频的相对位置
cv::CAP_PROP_FRAME_WIDTH 视频帧的像素宽度
cv::CAP_PROP_FRAME_HEIGHT 视频帧的像素高度
cv::CAP_PROP_FPS 录制视频的帧速率
cv::CAP_PROP_FOURCC 四个字符代码指示编解码
cv::CAP_PROP_FRAME_COUNT 视频文件的总帧数
cv::CAP_PROP_FORMAT 返回Mat对象的格式(如CV_8UC3)
cv::CAP_PROP_MODE 表示捕捉模式,值是特定于正在使用的视频后端(如DC1394)
cv::CAP_PROP_BRIGHTNESS相机的亮度设置
cv::CAP_PROP_CONCAT相机的对比度设置
cv::CAP_PROP_SATURATION相机的饱和度设置
cv::CAP_PROP_HUE相机的色调设置
cv::CAP_PROP_GAIN相机的增益设置
cv::CAP_PROP_EXPOSURE相机的曝光设置
cv::CAP_PROP_CONVERT_RGB如果非0,获取的图像将被转换为具有三个通道
cv::CAP_PROP_WHITE_BALANCE相机的白平衡设置
cv::CAP_PROP_RECTIFICATION立体相机整流标志(仅适用于DC1934-2.x)

使用cv::VideoWriter对象写入视频

cv::VideoWriter::VideoWriter(const string& filename, int fourcc, double fps, Size frame_size, bool is_color=true)

cv::VideoWriter::VideoWriter()

作用:创建一个VideoWriter对象,is_color为true则传入彩色图,反之可以传入灰度图。同样第二种形式不能直接使用,需要调用cv::VideoWriter::open()函数进行配置。

判断是否初始化成功,可通过cv::VideoWriter::isOpen()的返回值进行判断。

使用cv::VideoWriter::write()函数完成图像帧的写入

cv::VideoWriter::write(const Mat& img)

作用:完成图像帧的写入,图像必须和cv::VideoWriter具有相同的图像尺寸,如果是彩色必是三通道,反之使用单通道。

使用cv::VideoWriter::operator<<()将图像写入视频

cv::VideoWriter& cv::VideoWriter::operator<<(Mat& img)

作用:重载输出流操作符,将img存入视频文件。

数据存储

作为对标准视频压缩方式的补充,OpenCV提供了一种序列化与反序列化的机制,用于将不同数据类型的数据已YAML或XML格式写入磁盘或者从磁盘读取。这些方法可以用来加载或者保存任何OpenCV的数值变量到一个文件中。

cv::FileStorage的写入

cv::FileStorage::FileStorage(string filename, int flag)

cv::FileStorage::FileStorage()

作用:创建FileStorage对象(代表XML或YAML格式的数据文件),flag指定功能,写入时可为cv::FileStorage::WRITE和cv::FileStorage::APPEND。同样第二种形式不能直接使用,需要调用cv::FileStorage::open()函数进行配置。

写入时可以使用重载输出操作符函数cv::FileStorage::operator<<()进行写入。写完时调用cv::FileStorage::release()关闭该文件。

cv::FileStorage内部数据的存储形式主要有mapping和sequence,在最顶层是一个mapping,其中可以嵌套mapping和sequence。新建mapping或sequence分别使用{}和[]。

#include "stdafx.h"
#include <opencv2/opencv.hpp>
#include <time.h>// 使用cv::FileStorage创建一个test.yml参数文件
int main()
{// 创建FileStorage对象,实现其写入功能cv::FileStorage fs("test.yml", cv::FileStorage::WRITE);// 写入内容fs << "frameCount" << 5;// 获取当前时间并写入time_t rawtime;time(&rawtime);fs << "calibrationDate" << asctime(localtime(&rawtime));// 生成矩阵,并写入cv::Mat cameraMatrix = (cv::Mat_<double>(3, 3) << 1000, 0, 320, 0, 1000, 240, 0, 0, 1);cv::Mat distCoeffs = (cv::Mat_<double>(5, 1) << 0.1, 0.01, -0.001, 0, 0);fs << "cameraMatrix" << cameraMatrix << "distCoeffs" << distCoeffs;// 随机生成数及数组并写入fs << "features" << "[";for (int i = 0; i < 3; i++) {int x = rand() % 640;int y = rand() % 480;uchar lbp = rand() % 256;fs << "{:" << "x" << x << "y" << y << "lbp" << "[:";for (int j = 0; j < 8; j++) {fs << ((lbp >> j) & 1);}fs << "]" << "}";}fs << "]";// 关闭文件fs.release();return 0;
}

 用记事本打开test.yml文件,内容如下:

cv::FileStorage读取文件

cv::FileStorage::FileStorage(string filename, int flag)

cv::FileStorage::FileStorage()

作用:创建FileStorage对象(代表XML或YAML格式的数据文件),flag指定功能,读取时可为cv::FileStorage::READ。同样第二种形式不能直接使用,需要调用cv::FileStorage::open()函数进行配置。

读取时可以使用重载输出操作符函数cv::FileStorage::operator>>()进行读取,得到的不是直接的数据,而是FileNode对象。若该值是基本数据类型,则可以通过强制类型转换直接获取;若该值是mapping,则通过重载操作符[]并给定所需关键字访问;若该值是sequence,则通过重载操作符[]并给定整型参数访问,也可使用cv::FileStorageIterator迭代器进行访问。

读完时调用cv::FileStorage::release()关闭该文件。

cv::FileNode

FileNode的基本使用在上述内容中已做过介绍,下面将主要针对cv::FileStorageIterator进行介绍。

给定一个FileNode对象,通过cv::FileNode::begin()和cv::FileNode::end()可以分别返回该mapping或者sequence的首元素的迭代器和末尾首元素的迭代器。该迭代器对象可以通过cv::FileStorageIterator::operator*()来进行解引用操作并返回迭代器对应的位置的FileNode对象,并通过自增和自减来控制迭代器。

若其对一个mapping进行遍历,返回的FileNode对象将会有名字属性,可通过cv::FileNode::name()得到。同样,通过cv::FileNode::type()可获得cv::FileNode中定义的枚举类型。

cv::FileNode的成员函数
示例说明
cv::FileNode fn文件节点对象的默认构造函数
cv::FileNode fn1(fn0)文件节点对象的复制构造函数,从节点fn0创建节点fn1
cv::FileNode fn1(fs,node)文件节点对象构造函数,从C风格的CvFileStorage*指针和C风格的CvFileNode*指针节点创建FileNode对象

fn[ (string) key ]

fn[ (const char*) key ]

命名子串(映射节点)的STL字符串或C字符串存取器,将秘钥转换为适当的子节点。
fn[ (int) id ]子编号(序列节点)的访问;将ID转换为相应的子节点
fn.type()返回节点类型enum
fn.empty()确定节点是否为空
fn.isNone()确定节点是否为None
fn.isSeq()确定节点是否为序列
fn.isMap()确定节点是否为映射

fn.isInt()

fn.isReal()

fn.isString()

确定节点是否为整数

确定节点是否为浮点数

确定节点是否为字符串

fn.name()如果节点是映射的子节点,返回节点名称
size_t sz= fn.size()如果是序列或映射,返回节点中的元素数量,否则返回1。

(int) fn

(float) fn

(double) fn

(string) fn

从包含整数的节点中提取

从包含32位浮点数的节点中提取

从包含64位浮点数的节点中提取

从包含字符串的节点中提取

cv::FileNode::type()可能的返回值
示例说明
cv::FileNode::NONE = 0节点类型为None
cv::FileNode::INT = 1节点包含一个整数

cv::FileNode::REAL = 2

cv::FileNode::FLOAT = 2

节点包含一个浮点数(不分精度)

cv::FileNode::STR = 3

cv::FileNode::STRING = 3

节点包含一个字符串
cv::FileNode::REF = 4节点包含参考(即复合对象)
cv::FileNode::SEQ = 5节点本身是其他节点的序列
cv::FileNode::MAP = 6节点本身是其他节点的映射
cv::FileNode::FLOW = 8节点是序列或映射的紧凑表示
cv::FileNode::USER = 16节点是注册对象(如矩阵)
cv::FileNode::EMPTY = 32节点没有复制给它
cv::FileNode::NAMED = 64节点是映射的子节点(即它有一个名字)

注:一个FileNode除了拥有前8种属性之外还可以同时拥有最后四个中的一个或全部属性。

#include "stdafx.h"
#include <opencv2/opencv.hpp>// 使用FileStorage来读取test.yml文件
int main()
{// 创建FileStorage对象,实现读取功能cv::FileStorage fs("D:\\personal-data\\opencv\\example8-2\\example8-2\\test.yml", cv::FileStorage::READ);// 对FileNode进行强制类型转换,得到数据int frameCount = (int)fs["frameCount"];// 使用重载>>操作符std::string date;fs["calibrationDate"] >> date;cv::Mat cameraMatrix, distCoeffs;fs["cameraMatrix"] >> cameraMatrix;fs["distCoeffs"] >> distCoeffs;std::cout << "frameCount" << frameCount << std::endl;std::cout << "calibrationDate" << date << std::endl;std::cout << "cameraMatrix" << cameraMatrix << std::endl;std::cout << "distCoeffs" << distCoeffs << std::endl;cv::FileNode features = fs["features"];cv::FileNodeIterator it = features.begin(), it_end = features.end();int idx = 0;std::vector<uchar> lbpval;// 使用迭代器遍历序列for (; it != it_end; ++it, idx++){std::cout << "features #" << idx << ": ";std::cout << "x=" << (int)(*it)["x"] << ", y=" << (int)(*it)["y"] << ", lbp: (";(*it)["lbp"] >> lbpval;for (int i = 0; i < (int)lbpval.size(); i++){std::cout << " " << (int)lbpval[i];}std::cout << ")" << std::endl;}//关闭文件fs.release();return 0;
}

运行结果:

frameCount5
calibrationDateMon Aug 20 20:20:03 2018cameraMatrix[1000, 0, 320;0, 1000, 240;0, 0, 1]
distCoeffs[0.1;0.01;-0.001;0;0]
features #0: x=41, y=227, lbp: ( 0 1 1 1 1 1 0 1)
features #1: x=260, y=449, lbp: ( 0 0 1 1 0 1 1 0)
features #2: x=598, y=78, lbp: ( 0 1 0 0 1 0 1 0)

 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/491364.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

华为内部深度解读,关于5G发展的28个核心问题

来源 | 腾讯深网关于5G技术动态与商用进展业界最关心的核心问题&#xff0c;华为5G产品线相关负责人近日对《深网》等进行了详细解读&#xff0c;以下是《深网》整理的问答实录&#xff1a;一、5G先进性与行业应用1. 5G到底是什么&#xff1f;和4G比有什么不一样&#xff1f;从…

OpenCV鼠标事件和滑动条事件

鼠标事件 ① 鼠标事件是通过传统的回调函数机制来完成。 void your_mouse_callback(int event, int x, int y, int flags, void* param) 其中&#xff0c;第一个参数要指明事件&#xff0c;第二个和第三个参数是鼠标事件的位置&#xff0c;第四个参数是标志位&#xff0c;第…

GSMA:中国有望成为全球领先的5G市场之一

来源&#xff1a;GSMA移动智库近日&#xff0c;GSMA&#xff08;全球移动通信协会&#xff09;发布首个《中国移动经济发展报告2019》。报告称&#xff0c;中国的移动生态系统在2018年为中国经济创造了5.2万亿元 (7,500亿美元) 的附加值&#xff0c;相当于2018年中国GDP的5.5%。…

canal —— 阿里巴巴mysql数据库binlog的增量订阅消费组件

阿里巴巴mysql数据库binlog的增量订阅&消费组件canal &#xff0c;转载自 https://github.com/alibaba/canal 最新更新 canal QQ讨论群已经建立&#xff0c;群号&#xff1a;161559791 &#xff0c;欢迎加入进行技术讨论。canal消费端项目开源: Otter(分布式数据库同步系统…

OpenCV的滤波与卷积

目录 预备知识 滤波、核和卷积 边界外推和边界处理 阈值化操作 Otsu算法 自适应阈值 平滑 简单模糊和方框型滤波器 中值滤波器 高斯滤波器 双边滤波器 导数和梯度 索贝尔导数 Scharr滤波器 拉普拉斯变换 图像形态学 膨胀和腐蚀 通用形态学函数 开操作和闭操…

中国科协发布20个重大科学问题和工程技术难题

来源&#xff1a;晓艳的科技坊6月30日&#xff0c;中国科协在第二十一届中国科协年会闭幕式上发布了2019年20个对科学发展具有导向作用、对技术和产业创新具有关键作用的前沿科学问题和工程技术难题。   中国科学院院士、中国科协名誉主席韩启德表示&#xff0c;中国科协重大…

OpenCV常见的图像变换

拉伸、收缩、扭曲和旋转 最简单的图像变换是调整图像大小&#xff0c;使其变大或变小。但实际操作时要比想象的复杂一些&#xff0c;因为调整大小带来了像素如何插值&#xff08;放大&#xff09;或合并&#xff08;减少&#xff09;的问题。 均匀调整 cv::resize() void c…

边缘计算对于工业物联网的重要性

来源&#xff1a;物联网世界随着物联网的发展&#xff0c;工业制造设备所产生的数据量将越来越多。如果这些数据都要放到云端处理&#xff0c;就需要无穷无尽的频谱资源、传输带宽和数据处理能力&#xff0c;“云”难免不堪重负&#xff0c;此时就需要边缘计算来分担云计算的压…

全新算法助机器学习抵抗干扰

来源&#xff1a;科技日报 机器学习模型受到攻击将产生严重的后果&#xff0c;但如果对这一情形提前预防呢&#xff1f;就像人类针对即将到来的病毒去接种疫苗一样。据澳大利亚联邦科学与工业研究组织&#xff08;CSIRO&#xff09;官方网站消息&#xff0c;该机构的一个研究团…

磁共振成像技术发展简史丨科学史

来源&#xff1a;中国科学院苏州生物医学工程技术研究所编者按&#xff1a;核磁共振是一种常见的影像检查方式。全球首次为病人做核磁共振检查是在1977年7月3日。该技术是基于物理学家拉比有关测量原子核在磁场中性质的研究发展而来的。拉比在1988年去世前不久&#xff0c;也使…

最先进的AI还不如动物聪明?首届AI-动物奥运会英国开赛!

来源&#xff1a;animalaiolympics,新智元【导读】目前&#xff0c;即使是最先进的AI智能体&#xff0c;在适应环境变化的能力方面&#xff0c;还无法与动物相提并论。听上去很不可思议对不对&#xff0c;不服来比比看&#xff1f;日前&#xff0c;动物-AI奥运会正式拉开帷幕&a…

background-size 兼容ie8以下浏览器的方法

filter: progid:DXImageTransform.Microsoft.AlphaImageLoader(srcimgs/section-1.png, sizingMethodscale); -ms-filter:"progid:DXImageTransform.Microsoft.AlphaImageLoader(srcimgs/section-1.png, sizingMethodscale)";转载于:https://www.cnblogs.com/wend…

一文尽览5G全产业链及新机遇

来源&#xff1a;5G产业圈5G牌照的发放&#xff0c;对通信产业发展具有重要的战略意义。这不仅仅是为了5G商用&#xff0c;更赋予了多重目的。比如为了利用5G技术推动经济结构创新、促进经济增长、帮助华为中兴、结交爱立信诺基亚&#xff0c;分化高通英特尔……甚至可能是为了…

Windows10+Ubuntu 18.04.2+ROS 安装笔记(SSD单硬盘)上

Windows10Ubuntu 18.04.2ROS 安装笔记&#xff08;SSD单硬盘&#xff09;上一、前言二、化繁为简三、补充说明小结一、前言 最近需要学习ROS和python,于是便需要装Linux系统&#xff0c;于是选则了主流的 Ubuntu 18.04系统&#xff0c;同时与ROS 也是兼容性最好的系统。 之前…

实验室蒋田仔研究员:脑网络组图谱近10年研究详解【附PPT】

来源&#xff1a;模式识别国家重点实验室【导读】脑是人体最为复杂的器官&#xff0c;脑图谱是理解脑的结构和功能的基石。它为探索复杂的脑部结构和异常变化进行"导航"。因此&#xff0c;脑图谱绘制一直以来都是神经科学、认知科学、心理学和脑疾病研究的共同前沿领…

5G最完整的PPT

来源&#xff1a;云数据中心5G未来智能实验室是人工智能学家与科学院相关机构联合成立的人工智能&#xff0c;互联网和脑科学交叉研究机构。未来智能实验室的主要工作包括&#xff1a;建立AI智能系统智商评测体系&#xff0c;开展世界人工智能智商评测&#xff1b;开展互联网&a…

Windows10+Ubuntu 18.04.2+ROS 安装笔记(SSD单硬盘)下

Windows10Ubuntu 18.04.2ROS 安装笔记&#xff08;SSD单硬盘&#xff09;下一、前言二、化繁为简二、补充说明三、测试ROS 是否安装成功一、前言 最近需要学习ROS和python,于是便需要装Linux系统&#xff0c;于是选则了主流的 Ubuntu 18.04系统&#xff0c;同时与ROS 也是兼容…

了解宇宙万物的“第三种方法”​,人工智能正在改变科学

来源&#xff1a;quantamagazine编辑&#xff1a;张卓骏、luciana、笪洁琼、Aileen当今物理和天文实验所产生的海量信息&#xff0c;没有任何一个人或者团队可以完整的处理。有些实验数据每天以千兆字节的规模在增加——而且这个趋势只会越来越明显。想象一下&#xff0c;一台以…

pytorch的backward参数

首先&#xff0c;如果out.backward()中的out是一个标量的话&#xff08;相当于一个神经网络有一个样本&#xff0c;这个样本有两个属性&#xff0c;神经网络有一个输出&#xff09;那么此时我的backward函数是不需要输入任何参数的。 运行结果&#xff1a; 不难看出&#xff0c…

C#表格文字多收缩样式

C#表格文字多收缩样式 <style>.divOpen {height: 24px;overflow: hidden;} </style> ----------------- var html <div class"divOpen" οnclick"divClick(this)" style"cursor: pointer; min-width:100px;">;html value;ht…