OSG编程指南<十一>:OSG几何体操作及三维地形创建

1、简化几何体

  在 OSG 中,场景都是由基本的绘图基元构成的,基本的绘图基元构成简单的几何体,简单的几何体构成复杂的几何体,复杂的几何体最终构造成复杂的场景。当多个几何体组合时,可能
存在多种降低场景渲染效率的原因。在很多 3D 引擎中,都提供了对场景的几何体进行修改的操作,以达到最优渲染效率。虽然最优渲染效率只是一个理想状态,但一定的几何体操作在相当程度上可以提高渲染效率。
  在 OSG 中,为了获得所需的性能和渲染的效率,osgUtil 库提供了一些通用的几何体运算,这些几何体运算主要包括 osgUtil::Simplifier(简化)、osgUtil::SmoothingVisitor(生成法线)、osgUtil::DelaunayTriangulator(生成 Delaunay 三角网工具)和 osgUtil::TriStripVisitor(条带化)等。
  下面就来介绍几种常用的几何体操作。

1.1 osgUtil::Simplifier类

  简化几何体(osgUtil::Simplifier)类继承自 osg::NodeVisitor 类,它采用访问器的方式遍历几何体并对其进行简化处理,在后面的章节将会详细说明访问器的工作机制。osgUtil::Simplifier 类对几何体的简化主要需要设置两个方面的参数,即当几何体样本比率小于 1时,设置点的误差限制;当几何体的样本比率大于 1 时,设置边的长度限制。通过对点的误差或者边的长度的限制简化不必要的点和边,然后通过平滑处理和条带化渲染几何体,进而达到提高渲染效率的目的,也可以用于自动生成低层次模型。一般来说,样本比率越大,简化越少;样本比率越小,简化越多。优化可以直接调用下面的函数:

virtual void apply(osg::Geode &geode) //应用于叶节点
void simplify(osg::Geometry &geometry)//简化几何体

这两个函数同样可用于 osg::Node 节点,不过,关联实例时需要使用 accept()方法。osgUtil::Simplifier 简化采用的是边塌陷算法。

1.2 实例

在这里插入图片描述

1.3 实例源码

// OSGExamples.cpp : 定义控制台应用程序的入口点。
//#include "stdafx.h"#include <windows.h>
#include <osgViewer/Viewer>#include <osg/Node>
#include <osg/Geode>
#include <osg/Geometry>
#include <osg/Group>
#include <osg/Billboard>
#include <osg/Texture2D>
#include <osg/Image>
#include <osg/Vec3>
#include <osg/Vec2>
#include <osg/PositionAttitudeTransform>
#include <osg/MatrixTransform>
#include <osgDB/ReadFile>
#include <osgUtil/Optimizer>#include <osgViewer/ViewerEventHandlers> //事件监听
#include <osgGA/StateSetManipulator> //事件响应类,对渲染状态进行控制
#include <osgUtil/Simplifier> //简化几何体#pragma comment(lib, "OpenThreadsd.lib")
#pragma comment(lib, "osgd.lib")
#pragma comment(lib, "osgDBd.lib")
#pragma comment(lib, "osgUtild.lib")
#pragma comment(lib, "osgGAd.lib")
#pragma comment(lib, "osgViewerd.lib")
#pragma comment(lib, "osgTextd.lib")//读取模型
osg::Node *readModel()
{osg::ref_ptr<osg::Node> node = osgDB::readNodeFile("cow.osg");return node.release();
}//深拷贝并简化新模型
osg::Node *deepCopy(osg::Node *node)
{/*创建简化对象  simplifier(sampleRatio, maxError)参数:样本比率、点的误差或边的长度 样本比率<1 设置点的误差样本比率>1 设置边的长度限制   比率越大,简化越少  使用的是边塌陷算法*/float sampleRatio = 0.3f;float maxError = 4.0f;osgUtil::Simplifier simplifier(sampleRatio, maxError);//深拷贝osg::ref_ptr<osg::Node> deepnode = (osg::Node *)(node->clone(osg::CopyOp::DEEP_COPY_ALL));//创建一个位置变换节点,将之设置为新位置,将深拷贝的模型移到新位置osg::ref_ptr<osg::PositionAttitudeTransform> pat = new osg::PositionAttitudeTransform();pat->setPosition(osg::Vec3(10.0f, 0.0f, 0.0f));pat->addChild(deepnode);pat->accept(simplifier);return pat.release();
}int main()
{//创建一个叶节点对象并添加节点 osg::ref_ptr<osg::Group> root = new osg::Group();osg::ref_ptr<osg::Node> node1 = readModel();osg::ref_ptr<osg::Node> node2 = deepCopy(node1);root->addChild(node1);root->addChild(node2);//优化场景数据osgUtil::Optimizer optimizer;optimizer.optimize(root.get());//显示模型osg::ref_ptr<osgViewer::Viewer> viewer = new osgViewer::Viewer();//切换网格模式,方便比较viewer->addEventHandler(new osgGA::StateSetManipulator(viewer->getCamera()->getOrCreateStateSet()));viewer->addEventHandler(new osgViewer::StatsHandler());//实现状态信息统计viewer->addEventHandler(new osgViewer::WindowSizeHandler());viewer->setSceneData(root.get());viewer->realize();return viewer->run();
}

2、Delaunay 三角网绘制

  在数字地形建模中,不规则三角网(TIN)通过从不规则离散分布的数据点生成的连续三角面来逼近地形表面。就表达地形信息的角度而言,TIN 模型的优点是它能以不同层次的分辨率来描述地形表面。与格网数据模型相比,TIN 模型在某一特定分辨率下能用更少的空间和时间更精确地表示更加复杂的表面。特别是当地形包含有大量特征,如断裂线、构造线时,TIN 模型能更好地顾及这些特征,从而能更精确合理地表达地表形态。
对于 TIN 模型,其基本要求有以下 3 点:
(1)TIN 是唯一的。
(2)力求最佳三角形几何形状。
(3)保证最邻近的点构成三角形。

  在所有可能的三角网中,狄洛尼(Delaunay)三角网在地形拟合方面表现最为出色,常用于 TIN的生成。当不相交的断裂线等被作为预先定义的限制条件作用于 TIN 的生成当中时,就必须考虑带约束条件的狄洛尼三角网。
  目前,狄洛尼三角网生成的算法比较多,传统的算法主要包括两种,即 Lawson 算法以及Bowyer-Watson 算法。后来经过该传统算法改进的算法就多了,这里不专门对这些算法予以介绍,可参考相关论文。上面介绍了狄洛尼(Delaunay)三角网的特性、生成算法及应用,下面来看一下 OSG 中的狄洛尼三角网。

2.1 osgUtil::DelaunayTriangulator 类

  osgUtil::DelaunayTriangulator 类直接继承自 osg::Referenced 类,创建狄洛尼三角网有如下 3 个步骤:
(1)创建顶点数组
(2)创建一个 osgUtil::DelaunayTriangulator 对象,并初始化顶点数组,同时生成三角网,**程序代码如下:

bool triangulate()//开始生成三角网格

(3)创建一个几何体对象,把 osgUtil::DelaunayTriangulator 类对象生成的绘制图元加入到几何体中。在生成狄洛尼三角网时,还可以添加一些限制条件,限制条件可以是点、线或多边形,例如:

void addInputConstraint(DelaunayConstraint *dc)//添加限制条件

2.2 三角带绘制

  三角带绘制(osgUtil::TriStripVisitor)类继承自 osgUtil::BaseOptimizerVisitor 类,它采用访问器的机制遍历场景中的几何体,实现三角带绘制,以提高渲染效率。
  下面对 osgUtil::TriStripVisitor 的两个常用成员函数予以说明:

void stripify(osg::Geometry &drawable)//条带化几何体
virtual void apply(osg::Geode &geode)//应用于叶节点

从上面可以看出,它同样可应用于叶节点。值得注意的是,关联叶节点实例时需要调用 accept()
方法。
  大多数图形卡并不直接支持索引三角网。在渲染三角形时,一般是将 3 个顶点同时提交,这样,共享的顶点会多次提交,三角形用到一次就提交一次。因为内存和图形硬件间的数据传输是瓶颈,所以很多 API 和硬件支持特殊的三角网格式以减少传输量。基本思想是排序点和面,使显卡中已有的三角形不需要再次传输。
  这里,我们只讨论三角带,三角带是一个三角形列表,其中每个三角形都与前一个三角形共享一边。在一种最理想的状态下,三角带可以用 N+2 个顶点表示存储 N 个面。N 很大时,每个三角形平均发送一个顶点。在实践中,很多情况下,很多网格是一个三角带无法表达的,此时就需要多个三角带来联合绘制。因为我们希望最小化发往图形卡的顶点数,所以,三角带的数目应该尽可能得少,即三角带越长越好。从另一个方面来说,分别渲染两个长度为 N 的三角带所需要的时间比渲染一个长度为2N 的三角带要长,即使 2N 的三角带中三角形的个数多于两个分开的三角带中的三角形个数的和,因为建立各三角带需要额外的处理时间。

2.3 实例效果

在这里插入图片描述

2.4 源码

#include <windows.h>
#include <osgViewer/Viewer>#include <osg/Node>
#include <osg/Geode>
#include <osg/Geometry>
#include <osg/Group>
#include <osg/Billboard>
#include <osg/Texture2D>
#include <osg/Image>
#include <osg/Vec3>
#include <osg/Vec2>
#include <osg/PositionAttitudeTransform>
#include <osg/MatrixTransform>
#include <osgDB/ReadFile>
#include <osgUtil/Optimizer>#include <osgViewer/ViewerEventHandlers> //事件监听
#include <osgGA/StateSetManipulator> //事件响应类,对渲染状态进行控制
#include <osgUtil/Simplifier> //简化几何体
#include <osgUtil/DelaunayTriangulator> #pragma comment(lib, "OpenThreadsd.lib")
#pragma comment(lib, "osgd.lib")
#pragma comment(lib, "osgDBd.lib")
#pragma comment(lib, "osgUtild.lib")
#pragma comment(lib, "osgGAd.lib")
#pragma comment(lib, "osgViewerd.lib")
#pragma comment(lib, "osgTextd.lib")//Delaunay三角形
/*
创建顶点数组并添加数据  设置其他相关属性(可选)  创建osgUtil::DelaunayTriangulator类对象并生成三角网  创建几何体对象,把三角网类对象生成的绘制图元添加到几何体中
按w键显示网格化模型,可以看出网格密度不同  由于光照条件默认开启,旋转模型可以看出不同部位亮度显示不同  按l键显示关闭光照,旋转模型,可以看出亮度不变
*/int GetRandValue(int nMIN, int nMAX)
{int nMax = 1;nMax = RAND_MAX;//rand()函数随机数的最大值return (int)(rand() * (nMAX - nMIN) / nMax + nMIN);
}osg::ref_ptr <osg::Geode> createTriangulate()
{//创建顶点数组osg::ref_ptr<osg::Vec3Array> coords = new osg::Vec3Array();//添加顶点数据int nMin = -50;int nMax = 100;for (int i = -3000; i < 3000; i += 100){if (i < -1000){nMin = -100;nMax = 100;}else if (i > -1000 && i < 0){nMin = -60;nMax = 30;}else if (i > 0 && i < 500){nMin = -15;nMax = 10;}else if (i > 500 && i < 1000){nMin = -10;nMax = 10;}else if (i > 1000 && i < 1500){nMin = -20;nMax = 10;}else if (i > 15000){nMin = -80;nMax = 50;}for (int j = -3000; j < 3000; j += 100){float nZ = (float)GetRandValue(nMin, nMax);osg::Vec3 vertex(i, j, nZ);coords->push_back(vertex);}}//创建颜色数组osg::ref_ptr<osg::Vec4Array> color = new osg::Vec4Array();//添加颜色数据 for (unsigned int i = 0; i < 6000; i++){int nR = rand() % 10 + 2;color->push_back(osg::Vec4(0.0f, (double)nR / 10.0, 0.0f, 0.5f));}//创建Delaunay三角网对象osg::ref_ptr<osgUtil::DelaunayTriangulator> dt = new osgUtil::DelaunayTriangulator(coords.get());//生成三角网dt->triangulate();//创建几何体osg::ref_ptr<osg::Geometry> pGeometry = new osg::Geometry();//设置顶点数组pGeometry->setVertexArray(coords.get());//设置颜色数组pGeometry->setColorArray(color.get());//设置颜色的绑定方式为单个顶点pGeometry->setColorBinding(osg::Geometry::BIND_PER_VERTEX);//添加到绘图基元pGeometry->addPrimitiveSet(dt->getTriangles());osg::ref_ptr <osg::Geode> pGNode = new osg::Geode;pGNode->addChild(pGeometry);return pGNode.release();
}int main()
{//添加到根节点osg::ref_ptr<osg::Group> root = new osg::Group();root->addChild(createTriangulate());//优化场景数据osgUtil::Optimizer optimizer;optimizer.optimize(root.get());osg::ref_ptr<osgViewer::Viewer> viewer = new osgViewer::Viewer();//方便查看在多边形之间切换,以查看三角网viewer->addEventHandler(new osgGA::StateSetManipulator(viewer->getCamera()->getOrCreateStateSet()));viewer->addEventHandler(new osgViewer::StatsHandler());viewer->addEventHandler(new osgViewer::WindowSizeHandler());viewer->setSceneData(root.get());viewer->setUpViewInWindow(600, 600, 1000, 800);return viewer->run();
}

3、自动生成顶点法向量

  生成顶点法向量(osgUtil::SmoothingVisitor)类继承自 osg::NodeVisitor 类,它采用访问器机制,遍历场景中的几何体,生成顶点法向量。
下面对 osgUtil::SmoothingVisitor 的一个常用成员函数予以说明:

static void smooth(osg::Geometry &geoset)

  该函数用于生成顶点法向量,调用时需要注意,这是一个静态函数。在很多应用程序中,网格上的各点都需要一个表面法向量,它的用处非常广泛,例如:
计算光照。
背面剔除。
模拟粒子系统在表面的“弹跳”效果。
通过只需要正面而加速碰撞检测。

  通常我们在绘制几何体时都会指定法线。当得到一个模型,它本身并没有法向量时,则有必要通过现有的数据生成。通常,表面法向量可能保存于三角形级或顶点级,其中的一个技巧就是平均相邻三角形的表面法向量,并将结果标准化。当然,这要求知道三角形的法向量。一般可以这样假设,三角形的顶点按逆时针排列,通过叉积就可以计算外表面的法向量。当然,在有些情况下,顶点的顺序是未知且比较混乱的,这样就比较麻烦了。这个笔者也没有仔细深入研究,推荐读者看一下《计算非固定结构序列的多边形的顶点法线》这篇论文。通过平均三角形法向量求得顶点法向量是一种经验性的方法,不具有通用性。虽然在很多情况下都可以正确地工作,但有些情况下还是无法正常使用的,在使用布告板时,一定要注意这点,这时生成顶点法线的方法就会失效。因为布告板由两个三角形背靠构造而成,它的两个法向量是相反的,其平均值为 0,所以不能初始化,这时只能采用别的方法来处理,如“双面”三角形等。

4、OSG生成三维高程地形

  结合以上知识我们可以加入纹理制作一个三维地形文件。

4.1 地形效果

在这里插入图片描述

4.2 源码

#include <windows.h>
#include <osgViewer/Viewer>#include <osg/Node>
#include <osg/Geode>
#include <osg/Geometry>
#include <osg/Group>
#include <osg/Billboard>
#include <osg/Texture2D>
#include <osg/Image>
#include <osg/Vec3>
#include <osg/Vec2>
#include <osg/PositionAttitudeTransform>
#include <osg/MatrixTransform>
#include <osgDB/ReadFile>
#include <osgUtil/Optimizer>#include <osgViewer/ViewerEventHandlers> //事件监听
#include <osgGA/StateSetManipulator> //事件响应类,对渲染状态进行控制
#include <osgUtil/Simplifier> //简化几何体
#include <osgUtil/DelaunayTriangulator> 
#include <osgUtil/TriStripVisitor>
#include <osgUtil/SmoothingVisitor>#pragma comment(lib, "OpenThreadsd.lib")
#pragma comment(lib, "osgd.lib")
#pragma comment(lib, "osgDBd.lib")
#pragma comment(lib, "osgUtild.lib")
#pragma comment(lib, "osgGAd.lib")
#pragma comment(lib, "osgViewerd.lib")
#pragma comment(lib, "osgTextd.lib")//Delaunay三角形
/*
创建顶点数组并添加数据  设置其他相关属性(可选)  创建osgUtil::DelaunayTriangulator类对象并生成三角网  创建几何体对象,把三角网类对象生成的绘制图元添加到几何体中
按w键显示网格化模型,可以看出网格密度不同  由于光照条件默认开启,旋转模型可以看出不同部位亮度显示不同  按l键显示关闭光照,旋转模型,可以看出亮度不变
*/int GetRandValue(int nMIN, int nMAX)
{int nMax = 1;nMax = RAND_MAX;//rand()函数随机数的最大值return (int)(rand() * (nMAX - nMIN) / nMax + nMIN);
}osg::ref_ptr <osg::Geometry> createTriangulate()
{//创建顶点数组osg::ref_ptr<osg::Vec3Array> verTexs = new osg::Vec3Array();//添加顶点数据int nMin = -50;int nMax = 100;for (int i = -3000; i < 3000; i += 100){if (i < -1000){nMin = -100;nMax = 100;}else if (i > -1000 && i < 0){nMin = -60;nMax = 30;}else if (i > 0 && i < 500){nMin = -15;nMax = 10;}else if (i > 500 && i < 1000){nMin = -10;nMax = 10;}else if (i > 1000 && i < 1500){nMin = -20;nMax = 10;}else if (i > 15000){nMin = -80;nMax = 50;}for (int j = -3000; j < 3000; j += 100){float nZ = (float)GetRandValue(nMin, nMax);osg::Vec3 vertex(i, j, nZ);verTexs->push_back(vertex);}}//创建颜色数组osg::ref_ptr<osg::Vec4Array> color = new osg::Vec4Array();//添加颜色数据 for (unsigned int i = 0; i < 6000; i++){int nR = rand() % 10 + 2;color->push_back(osg::Vec4(0.0f, (double)nR / 10.0, 0.0f, 0.5f));}//创建Delaunay三角网对象osg::ref_ptr<osgUtil::DelaunayTriangulator> dt = new osgUtil::DelaunayTriangulator(verTexs.get());//生成三角网dt->triangulate();//创建几何体osg::ref_ptr<osg::Geometry> pGeometry = new osg::Geometry();//设置顶点数组pGeometry->setVertexArray(verTexs.get());osg::ref_ptr<osg::Image> sImagePath = osgDB::readImageFile("D:\\Terrain.png");if (sImagePath.get()){osg::ref_ptr<osg::Texture2D> texture2D = new osg::Texture2D;texture2D->setImage(sImagePath.get());//绑定纹理后,释放内部的ref_ptr<Image>,删除image图像texture2D->setUnRefImageDataAfterApply(true);//建立纹理顶点osg::ref_ptr<osg::Vec2Array> pVec2Array = new osg::Vec2Array;for (int i = -3000; i < 3000; i += 100){for (int j = -3000; j < 3000; j += 100){osg::Vec2 textCoord(0.0, 0.0);textCoord.x() = (double)(j + 3000.0) / 6000.0;textCoord.y() = (double)(i + 3000.0) / 6000.0;pVec2Array->push_back(textCoord);}}//Texture类关联到渲染状态StateSetosg::ref_ptr<osg::StateSet> pStateSet = pGeometry->getOrCreateStateSet();//将纹理关联给StateSet纹理单元0、osg::StateAttribute::OFF关闭纹理pStateSet->setTextureAttributeAndModes(0, texture2D.get(), osg::StateAttribute::ON);pGeometry->setTexCoordArray(0, pVec2Array.get());//建立法线数组normal,垂直于Z轴负方向//osg::ref_ptr<osg::Vec3Array> pVec3ArrayNormal = new osg::Vec3Array;//pGeometry->setNormalArray(pVec3ArrayNormal.get());//pGeometry->setNormalBinding(osg::Geometry::BIND_OVERALL);//pVec3ArrayNormal->push_back(osg::Vec3(0.0, 0.0, 1.0));pGeometry->setStateSet(pStateSet);}else{//设置颜色数组pGeometry->setColorArray(color.get());//设置颜色的绑定方式为单个顶点pGeometry->setColorBinding(osg::Geometry::BIND_PER_VERTEX);}//添加到绘图基元pGeometry->addPrimitiveSet(dt->getTriangles());return pGeometry.release();
}int main()
{//添加到根节点osg::ref_ptr<osg::Group> root = new osg::Group();osg::ref_ptr <osg::Geode> pGNode = new osg::Geode;//创建一个几何体对象osg::ref_ptr<osg::Geometry> geometry = createTriangulate();//自动生成顶点法线osgUtil::SmoothingVisitor::smooth(*(geometry.get()));//对几何体进行条带化osgUtil::TriStripVisitor stripper;stripper.stripify(*(geometry.get()));pGNode->addChild(geometry.get());root->addChild(pGNode);//优化场景数据osgUtil::Optimizer optimizer;optimizer.optimize(root.get());osg::ref_ptr<osgViewer::Viewer> viewer = new osgViewer::Viewer();//方便查看在多边形之间切换,以查看三角网viewer->addEventHandler(new osgGA::StateSetManipulator(viewer->getCamera()->getOrCreateStateSet()));viewer->addEventHandler(new osgViewer::StatsHandler());viewer->addEventHandler(new osgViewer::WindowSizeHandler());viewer->setSceneData(root.get());viewer->setUpViewInWindow(600, 600, 1000, 800);return viewer->run();
}

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

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

相关文章

JAVA小游戏“简易版王者荣耀”

第一步是创建项目 项目名自拟 第二部创建个包名 来规范class 然后是创建类 GameFrame 运行类 package com.sxt;import java.awt.Graphics; import java.awt.Image; import java.awt.Toolkit; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; im…

Scope 模块

Scope 模块可以连接任何类型的实数信号线 (不支持复数)。 波形显示界面主要包括两个部分: Scope 独有的工具栏、波形显示区域。 波形显示界面默认是黑色背景, 当有单个信号输入时, 信号线是黄色的。 Scope 模块也有菜单栏, 只不过默认将其句柄和显示都隐藏起来, 可以通过下面…

5 个适用于 Windows 的顶级免费数据恢复软件

对于计算机来说&#xff0c;最重要的是用户数据。除了您的数据之外&#xff0c;有关计算机的其他所有内容都是可替换的。这三个是数据丢失的最常见原因&#xff1a; 文件/文件夹删除丢失分区分区损坏 文件/文件夹删除 文件/文件夹删除是最常见的数据丢失类型。大多数时候&am…

《微信小程序开发从入门到实战》学习三十一

3.4 开发参与投票页面 3.4.9 显示投票结果 在实际使用中&#xff0c;一个用户不能对同一个投票进行重复提交&#xff0c;因此需要向服务器端提交投票结果和提交用户ID。另外页面&#xff0c;需要完善。用户提交完投票后 &#xff0c;还需要显示投票目前的结果&#xff0c;提交…

C语言进阶之笔试题详解(1)

引言&#xff1a; 对指针知识进行简单的回顾&#xff0c;然后再完成笔试题。 ✨ 猪巴戒&#xff1a;个人主页✨ 所属专栏&#xff1a;《C语言进阶》 &#x1f388;跟着猪巴戒&#xff0c;一起学习C语言&#x1f388; 目录 引言&#xff1a; 知识简单回顾 指针是什么 指针变…

1 时间序列模型入门: LSTM

0 前言 循环神经网络&#xff08;Recurrent Neural Network&#xff0c;RNN&#xff09;是一种用于处理序列数据的神经网络。相比一般的神经网络来说&#xff0c;他能够处理序列变化的数据。比如某个单词的意思会因为上文提到的内容不同而有不同的含义&#xff0c;RNN就能够很好…

2023-3年CSDN创作纪念日

机缘 今天开开心心出门去上班&#xff0c;就收到了一个csdn私信&#xff0c;打开一看说是给我惊喜来着&#xff0c;我心想csdn还能给惊喜&#xff1f;以为是有什么奖品或者周边之类的&#xff0c;结果什么也没有&#xff0c;打开就是一份信&#x1f602;。 也挺不错的&#xf…

1.6 C语言之数组概述

1.6 C语言之数组概述 一、数组二、练习 一、数组 所谓数组&#xff0c;就是内存中一片连续的空间&#xff0c;可以用来存储一组同类型的数据 数组有下标&#xff0c;从0开始&#xff0c;可以理解为是给数组中的元素编号&#xff0c;便于后续寻址访问 我们来编写一个程序&…

SparkSQL之Optimized LogicalPlan生成过程

经过Analyzer的处理&#xff0c;Unresolved LogicalPlan已经解析成为Analyzed LogicalPlan。Analyzed LogicalPlan中自底向上节点分别对应Relation、Subquery、Filter和Project算子。   Analyzed LogicalPlan基本上是根据Unresolved LogicalPlan一对一转换过来的&#xff0c;…

针对哈希冲突的解决方法

了解哈希表和哈希冲突是什么 哈希表&#xff1a;是一种实现关联数组抽象数据类型的数据结构&#xff0c;这种结构可以将关键码映射到给定值。简单来说哈希表&#xff08;key-value&#xff09;之间存在一个映射关系&#xff0c;是键值对的关系&#xff0c;一个键对应一个值。 …

foobar2000 突然无法正常输出DSD信号

之前一直在用foobar2000加外置dac听音乐&#xff0c;有一天突然发现听dsd的时候&#xff0c;dac面板显示输出的是PCM格式信号&#xff0c;而不是DSD信号&#xff0c;这让我觉得很奇怪&#xff0c;反复折腾了几次&#xff0c;卸载安装驱动什么的&#xff0c;依然如此&#xff0c…

java协同过滤算法 springboot+vue游戏推荐系统

随着人们生活质量的不断提高以及个人电脑和网络的普及&#xff0c;人们的业余生活质量要求也在不断提高&#xff0c;选择一款好玩&#xff0c;精美&#xff0c;画面和音质&#xff0c;品质优良的休闲游戏已经成为一种流行的休闲方式。可以说在人们的日常生活中&#xff0c;除了…

k8s集群资源监控工具metrics-server安装

1、下载镜像 docker pull swr.cn-east-2.myhuaweicloud.com/kuboard-dependency/metrics-server:v0.6.22、在任一一个主节点上创建角色&#xff0c;执行下面语句 kubectl create clusterrolebinding kube-proxy-cluster-admin --clusterrolecluster-admin --usersystem:kube-…

Int8量化算子在移动端CPU的性能优化

本文介绍了Depthwise Convolution 的Int8算子在移动端CPU上的性能优化方案。ARM架构的升级和相应指令集的更新不断提高移动端各算子的性能上限&#xff0c;结合数据重排和Sdot指令能给DepthwiseConv量化算子的性能带来较大提升。 背景 MNN对ConvolutionDepthwise Int8量化算子在…

Shell脚本:Linux Shell脚本学习指南(第三部分Shell高级)二

七、Shell Here String&#xff08;内嵌字符串&#xff0c;嵌入式字符串&#xff09; Here String 是《六、Shell Here Document&#xff08;内嵌文档/立即文档&#xff09;》的一个变种&#xff0c;它的用法如下&#xff1a; command <<< string command 是 Shell 命…

JavaScript如何实现钟表效果,时分秒针指向当前时间,并显示当前年月日,及2024春节倒计时,源码奉上

本篇有运用jQuery&#xff0c;记得引入jQuery库&#xff0c;否则不会执行的喔~ <!DOCTYPE html> <html> <head> <meta charset"utf-8"> <title></title> <meta name"chenc" content"Runoob"> <met…

element-ui表格无法横向拖动问题

是不是用到了fixed // 因为我只有在小屏显示不下的时候才会出现这个问题所以我在这里做了适配(建议把样式放在全局) media screen and (max-width: 1800px) {// 由于使用了fixed导致横向条无法拖动出现bug.Table-page .el-table__fixed {height: auto !important;bottom: 2px …

计算机编程基础教程,中文编程工具下载,编程构件组合按钮

计算机编程基础教程&#xff0c;中文编程工具下载&#xff0c;编程构件组合按钮 给大家分享一款中文编程工具&#xff0c;零基础轻松学编程&#xff0c;不需英语基础&#xff0c;编程工具可下载。 这款工具不但可以连接部分硬件&#xff0c;而且可以开发大型的软件&#xff0c…

开卷翻到毒蘑菇?浅谈大模型检索增强(RAG)的鲁棒性

©PaperWeekly 原创 作者 | 陈思硕 单位 | 北京大学 研究方向 | 自然语言处理 很久没有写论文 notes 了&#xff0c;近期因为参与对检索增强生成&#xff08;Retrieval-Augmented Generation, RAG&#xff09;范式鲁棒性的研究&#xff0c;注意到了近两个月来社区中涌现了…