Easy-Es操作Elasticsearch

文章目录

  • 1 Easy-Es
    • 1.1 简介
    • 1.2 MySQL与Easy-Es语法对比
    • 1.3 集成及配置
      • 1.3.1 pom.xml
      • 1.3.2 配置
    • 1.4 使用
      • 1.4.1 注解的使用
      • 1.4.2 EsMapper接口
      • 1.4.3 简单搜索
    • 1.5 使用案例
      • 1.5.1 综合商品搜索
      • 1.5.2 相关商品推荐
      • 1.5.3 聚合搜索商品相关信息

1 Easy-Es

使用过Spring Data操作ES的小伙伴应该有所了解,它只能实现一些非常基本的数据管理工作,一旦遇到稍微复杂点的查询,基本都要依赖ES官方提供的RestHighLevelClientSpring Data只是在其基础上进行了简单的封装。最近发现一款更优雅的ES ORM框架Easy-Es,使用它能像MyBatis-Plus一样操作ES

点击了解 SpringBoot 整合ElasticSearch

1.1 简介

Easy-Es(简称EE)是一款基于Elasticsearch(简称ES)官方提供的RestHighLevelClient打造的ORM开发框架,在RestHighLevelClient的基础上,只做增强不做改变,为简化开发、提高效率而生。EEMybatis-Plus(简称MP)的用法非常相似,如果你之前使用过MP的话,应该能很快上手EE。EE的理念是:把简单、易用、方便留给用户,把复杂留给框架。
官网地址:https://www.easy-es.cn/

EE的主要特性如下:

  • 全自动索引托管:开发者无需关心索引的创建、更新及数据迁移等繁琐步骤,框架能自动完成。
  • 屏蔽语言差异:开发者只需要会MySQL的语法即可使用ES。
  • 代码量极少:与直接使用官方提供的RestHighLevelClient相比,相同的查询平均可以节省3-5倍的代码量。
  • 零魔法值:字段名称直接从实体中获取,无需手写。
  • 零额外学习成本: 开发者只要会国内最受欢迎的Mybatis-Plus用法,即可无缝迁移至EE。

1.2 MySQL与Easy-Es语法对比

首先我们来对MySQLEasy-EsRestHighLevelClient的语法做过对比,来快速学习下Easy-Es的语法。

MySQLEasy-Eses-DSL/es java api
andandmust
ororshould
=eqterm
!=neboolQueryBuilder.mustNot(queryBuilder)
>gtQueryBuilders.rangeQuery(‘es field’).gt()
>=geQueryBuilders.rangeQuery(‘es field’).gte()
<ltQueryBuilders.rangeQuery(‘es field’).lt()
<=leQueryBuilders.rangeQuery(‘es field’).lte()
like ‘%field%’likeQueryBuilders.wildcardQuery(field,value)
not like ‘%field%’notLikemust not wildcardQuery(field,value)
like ‘%field’likeLeftQueryBuilders.wildcardQuery(field,*value)
like ‘field%’likeRightQueryBuilders.wildcardQuery(field,value*)
betweenbetweenQueryBuilders.rangeQuery(‘es field’).from(xx).to(xx)
notBetweennotBetweenmust not QueryBuilders.rangeQuery(‘es field’).from(xx).to(xx)
is nullisNullmust not QueryBuilders.existsQuery(field)
is notNullisNotNullQueryBuilders.existsQuery(field)
ininQueryBuilders.termsQuery(" xx es field", xx)
not innotInmust not QueryBuilders.termsQuery(" xx es field", xx)
group bygroupByAggregationBuilders.terms()
order byorderByfieldSortBuilder.order(ASC/DESC)
minminAggregationBuilders.min
maxmaxAggregationBuilders.max
avgavgAggregationBuilders.avg
sumsumAggregationBuilders.sum
order by xxx ascorderByAscfieldSortBuilder.order(SortOrder.ASC)
order by xxx descorderByDescfieldSortBuilder.order(SortOrder.DESC)
-matchmatchQuery
-matchPhraseQueryBuilders.matchPhraseQuery
-matchPrefixQueryBuilders.matchPhrasePrefixQuery
-queryStringQueryQueryBuilders.queryStringQuery
select *matchAllQueryQueryBuilders.matchAllQuery()
-highLightHighlightBuilder.Field

1.3 集成及配置

1.3.1 pom.xml

<dependency><groupId>cn.easy-es</groupId><artifactId>easy-es-boot-starter</artifactId><version>1.0.2</version>
</dependency>

由于底层使用了ES官方提供的RestHighLevelClient,这里ES的相关依赖版本需要统一下,这里使用的ES客户端版本为7.14.0,ES版本为7.17.3;

<dependencyManagement><dependencies><dependency><groupId>org.elasticsearch.client</groupId><artifactId>elasticsearch-rest-high-level-client</artifactId><version>7.14.0</version></dependency><dependency><groupId>org.elasticsearch</groupId><artifactId>elasticsearch</artifactId><version>7.14.0</version></dependency></dependencies>
</dependencyManagement>

1.3.2 配置

再修改配置文件application.ymlEasy-Es进行配置。

easy-es:# 是否开启EE自动配置enable: true# ES连接地址+端口address: localhost:9200# 关闭自带bannerbanner: false

添加Easy-EsJava配置,使用@EsMapperScan配置好Easy-EsMapper接口和文档对象路径,如果使用了MyBatis-Plus的话,需要和它的扫描路径区分开来。

/*** EasyEs配置类*/
@Configuration
@EsMapperScan("com.test.easyes")
public class EasyEsConfig {
}

1.4 使用

Easy-Es集成和配置完成后,就可以开始使用了。

1.4.1 注解的使用

下面我们来学习下Easy-Es中注解的使用。
首先我们需要创建文档对象EsProduct,然后给类和字段添加上Easy-Es的注解;

/*** 搜索商品的信息*/
@Data
@EqualsAndHashCode
@IndexName(value = "pms", shardsNum = 1, replicasNum = 0)
public class EsProduct implements Serializable {private static final long serialVersionUID = -1L;@IndexId(type = IdType.CUSTOMIZE)private Long id;@IndexField(fieldType = FieldType.KEYWORD)private String productSn;private Long brandId;@IndexField(fieldType = FieldType.KEYWORD)private String brandName;private Long productCategoryId;@IndexField(fieldType = FieldType.KEYWORD)private String productCategoryName;private String pic;@IndexField(fieldType = FieldType.TEXT, analyzer = "ik_max_word")private String name;@IndexField(fieldType = FieldType.TEXT, analyzer = "ik_max_word")private String subTitle;@IndexField(fieldType = FieldType.TEXT, analyzer = "ik_max_word")private String keywords;private BigDecimal price;private Integer sale;private Integer newStatus;private Integer recommandStatus;private Integer stock;private Integer promotionType;private Integer sort;@IndexField(fieldType = FieldType.NESTED, nestedClass = EsProductAttributeValue.class)private List<EsProductAttributeValue> attrValueList;@Scoreprivate Float score;
}/*** 嵌套类型EsProductAttributeValue* 搜索商品的属性信息*/
@Data
@EqualsAndHashCode
public class EsProductAttributeValue implements Serializable {private static final long serialVersionUID = 1L;@IndexField(fieldType = FieldType.LONG)private Long id;@IndexField(fieldType = FieldType.KEYWORD)private Long productAttributeId;//属性值@IndexField(fieldType = FieldType.KEYWORD)private String value;//属性参数:0->规格;1->参数@IndexField(fieldType = FieldType.INTEGER)private Integer type;//属性名称@IndexField(fieldType=FieldType.KEYWORD)private String name;
}

EsProduct 中的注解具体说明如下:

  • @IndexName:索引名注解,value是指定索引名;shardsNum:分片数;replicasNum:副本数
  • @IndexIdES主键注解,type 指定注解类型,CUSTOMIZE 表示自定义
  • @IndexFieldES字段注解,fieldType 字段在索引中的类型,analyzer 索引文档时用的分词器,nestedClass 嵌套类
  • @Score:得分注解 decimalPlaces 得分保留小数位,实体类中被作为 ES 查询得分返回的字段使用

1.4.2 EsMapper接口

下面我们来实现几个简单的商品信息维护接口,包括商品信息的导入、创建和删除。
首先我们需要定义一个Mapper,继承BaseEsMapper

/*** 商品ES操作类*/
public interface EsProductMapper extends BaseEsMapper<EsProduct> {}

然后在Service实现类中直接使用EsProductMapper内置方法实现即可

/*** 搜索商品管理Service实现类*/
@Service
public class EsProductServiceImpl implements EsProductService {@Autowiredprivate EsProductDao productDao;@Autowiredprivate EsProductMapper esProductMapper;@Overridepublic int importAll() {List<EsProduct> esProductList = productDao.getAllEsProductList(null);return esProductMapper.insertBatch(esProductList);}@Overridepublic void delete(Long id) {esProductMapper.deleteById(id);}@Overridepublic EsProduct create(Long id) {EsProduct result = null;List<EsProduct> esProductList = productDao.getAllEsProductList(id);if (esProductList.size() > 0) {result = esProductList.get(0);esProductMapper.insert(result);}return result;}@Overridepublic void delete(List<Long> ids) {if (!CollectionUtils.isEmpty(ids)) {esProductMapper.deleteBatchIds(ids);}}
}

1.4.3 简单搜索

下面我们来实现一个最简单的商品搜索,分页搜索商品名称、副标题、关键词中包含指定关键字的商品。

通过QueryWrapper来构造查询条件,然后使用Mapper中的方法来进行查询,使用过MyBatis-Plus的小伙伴应该很熟悉了

/*** 搜索商品管理Service实现类*/
@Service
public class EsProductServiceImpl implements EsProductService {@Autowiredprivate EsProductMapper esProductMapper;@Overridepublic PageInfo<EsProduct> search(String keyword, Integer pageNum, Integer pageSize) {LambdaEsQueryWrapper<EsProduct> wrapper = new LambdaEsQueryWrapper<>();if(StrUtil.isEmpty(keyword)){wrapper.matchAllQuery();}else{wrapper.multiMatchQuery(keyword,EsProduct::getName,EsProduct::getSubTitle,EsProduct::getKeywords);}return esProductMapper.pageQuery(wrapper, pageNum, pageSize);}
}

在控制台输出查看生成的DSL语句
在这里插入图片描述
DSL语句直接复制到 Kibana 中即可执行查看结果了,这和我们手写DSL语句没什么两样的。
图片

1.5 使用案例

1.5.1 综合商品搜索

下面我们来实现一个复杂的商品搜索,涉及到过滤、不同字段匹配权重不同以及可以进行排序。

首先来说需求,按输入的关键字搜索商品名称(权重10)、副标题(权重5)和关键词(权重2),可以按品牌和分类进行筛选,可以有5种排序方式,默认按相关度进行排序

下面是使用Easy-Es的实现方式

/*** 搜索商品管理Service实现类*/
@Service
public class EsProductServiceImpl implements EsProductService {@Autowiredprivate EsProductMapper esProductMapper;@Overridepublic PageInfo<EsProduct> search(String keyword, Long brandId, Long productCategoryId, Integer pageNum, Integer pageSize,Integer sort) {LambdaEsQueryWrapper<EsProduct> wrapper = new LambdaEsQueryWrapper<>();//过滤if (brandId != null || productCategoryId != null) {if (brandId != null) {wrapper.eq(EsProduct::getBrandId,brandId);}if (productCategoryId != null) {wrapper.eq(EsProduct::getProductCategoryId,productCategoryId).enableMust2Filter(true);}}//搜索if (StrUtil.isEmpty(keyword)) {wrapper.matchAllQuery();} else {wrapper.and(i -> i.match(EsProduct::getName, keyword, 10f).or().match(EsProduct::getSubTitle, keyword, 5f).or().match(EsProduct::getKeywords, keyword, 2f));}//排序if(sort==1){//按新品从新到旧wrapper.orderByDesc(EsProduct::getId);}else if(sort==2){//按销量从高到低wrapper.orderByDesc(EsProduct::getSale);}else if(sort==3){//按价格从低到高wrapper.orderByAsc(EsProduct::getPrice);}else if(sort==4){//按价格从高到低wrapper.orderByDesc(EsProduct::getPrice);}else{//按相关度wrapper.sortByScore(SortOrder.DESC);}return esProductMapper.pageQuery(wrapper, pageNum, pageSize);}
}

1.5.2 相关商品推荐

当我们查看相关商品的时候,一般底部会有一些商品推荐,这里简单来实现下。

首先来说下需求,可以根据指定商品的ID来查找相关商品
这里我们的实现原理是这样的:首先根据ID获取指定商品信息,然后以指定商品的名称、品牌和分类来搜索商品,并且要过滤掉当前商品,调整搜索条件中的权重以获取最好的匹配度;

/*** 搜索商品管理Service实现类*/
@Service
public class EsProductServiceImpl implements EsProductService {@Autowiredprivate EsProductMapper esProductMapper;@Overridepublic PageInfo<EsProduct> recommend(Long id, Integer pageNum, Integer pageSize) {LambdaEsQueryWrapper<EsProduct> wrapper = new LambdaEsQueryWrapper<>();List<EsProduct> esProductList = productDao.getAllEsProductList(id);if (esProductList.size() > 0) {EsProduct esProduct = esProductList.get(0);String keyword = esProduct.getName();Long brandId = esProduct.getBrandId();Long productCategoryId = esProduct.getProductCategoryId();//用于过滤掉相同的商品wrapper.ne(EsProduct::getId,id);//根据商品标题、品牌、分类进行搜索wrapper.and(i -> i.match(EsProduct::getName, keyword, 8f).or().match(EsProduct::getSubTitle, keyword, 2f).or().match(EsProduct::getKeywords, keyword, 2f).or().match(EsProduct::getBrandId, brandId, 5f).or().match(EsProduct::getProductCategoryId, productCategoryId, 3f));return esProductMapper.pageQuery(wrapper, pageNum, pageSize);}return esProductMapper.pageQuery(wrapper, pageNum, pageSize);}
}

1.5.3 聚合搜索商品相关信息

在搜索商品时,经常会有一个筛选界面来帮助我们找到想要的商品,这里我们来简单实现下。

首先来说下需求,可以根据搜索关键字获取到与关键字匹配商品相关的分类、品牌以及属性

这里我们可以使用ES的聚合来实现,搜索出相关商品,聚合出商品的品牌、商品的分类以及商品的属性,只要出现次数最多的前十个即可;

由于Easy-Es目前只用groupBy实现了简单的聚合,对于我们这种有嵌套对象的聚合无法支持,所以需要使用RestHighLevelClient来实现,如果对照之前的Spring Data实现方式的话,可以发现用法差不多,看样子Spring Data只是做了简单的封装而已。

/*** 搜索商品管理Service实现类*/
@Service
public class EsProductServiceImpl implements EsProductService {@Autowiredprivate EsProductMapper esProductMapper;@Overridepublic EsProductRelatedInfo searchRelatedInfo(String keyword) {SearchRequest searchRequest = new SearchRequest();searchRequest.indices("pms_*");SearchSourceBuilder builder = new SearchSourceBuilder();//搜索条件if (StrUtil.isEmpty(keyword)) {builder.query(QueryBuilders.matchAllQuery());} else {builder.query(QueryBuilders.multiMatchQuery(keyword, "name", "subTitle", "keywords"));}//聚合搜索品牌名称builder.aggregation(AggregationBuilders.terms("brandNames").field("brandName"));//集合搜索分类名称builder.aggregation(AggregationBuilders.terms("productCategoryNames").field("productCategoryName"));//聚合搜索商品属性,去除type=1的属性AbstractAggregationBuilder<NestedAggregationBuilder> aggregationBuilder = AggregationBuilders.nested("allAttrValues", "attrValueList").subAggregation(AggregationBuilders.filter("productAttrs", QueryBuilders.termQuery("attrValueList.type", 1)).subAggregation(AggregationBuilders.terms("attrIds").field("attrValueList.productAttributeId").subAggregation(AggregationBuilders.terms("attrValues").field("attrValueList.value")).subAggregation(AggregationBuilders.terms("attrNames").field("attrValueList.name"))));builder.aggregation(aggregationBuilder);searchRequest.source(builder);try {SearchResponse searchResponse = esProductMapper.search(searchRequest, RequestOptions.DEFAULT);return convertProductRelatedInfo(searchResponse);} catch (IOException e) {e.printStackTrace();}return null;}/*** 将返回结果转换为对象*/private EsProductRelatedInfo convertProductRelatedInfo(SearchResponse response) {EsProductRelatedInfo productRelatedInfo = new EsProductRelatedInfo();Map<String, Aggregation> aggregationMap = response.getAggregations().asMap();//设置品牌Aggregation brandNames = aggregationMap.get("brandNames");List<String> brandNameList = new ArrayList<>();for(int i = 0; i<((Terms) brandNames).getBuckets().size(); i++){brandNameList.add(((Terms) brandNames).getBuckets().get(i).getKeyAsString());}productRelatedInfo.setBrandNames(brandNameList);//设置分类Aggregation productCategoryNames = aggregationMap.get("productCategoryNames");List<String> productCategoryNameList = new ArrayList<>();for(int i=0;i<((Terms) productCategoryNames).getBuckets().size();i++){productCategoryNameList.add(((Terms) productCategoryNames).getBuckets().get(i).getKeyAsString());}productRelatedInfo.setProductCategoryNames(productCategoryNameList);//设置参数Aggregation productAttrs = aggregationMap.get("allAttrValues");List<? extends Terms.Bucket> attrIds = ((ParsedStringTerms) ((ParsedFilter) ((ParsedNested) productAttrs).getAggregations().get("productAttrs")).getAggregations().get("attrIds")).getBuckets();List<EsProductRelatedInfo.ProductAttr> attrList = new ArrayList<>();for (Terms.Bucket attrId : attrIds) {EsProductRelatedInfo.ProductAttr attr = new EsProductRelatedInfo.ProductAttr();attr.setAttrId(Long.parseLong((String) attrId.getKey()));List<String> attrValueList = new ArrayList<>();List<? extends Terms.Bucket> attrValues = ((ParsedStringTerms) attrId.getAggregations().get("attrValues")).getBuckets();List<? extends Terms.Bucket> attrNames = ((ParsedStringTerms) attrId.getAggregations().get("attrNames")).getBuckets();for (Terms.Bucket attrValue : attrValues) {attrValueList.add(attrValue.getKeyAsString());}attr.setAttrValues(attrValueList);if(!CollectionUtils.isEmpty(attrNames)){String attrName = attrNames.get(0).getKeyAsString();attr.setAttrName(attrName);}attrList.add(attr);}productRelatedInfo.setProductAttrs(attrList);return productRelatedInfo;}
}

使用 Easy-Es 确实简单,但是对于复杂的聚合搜索功能,需要使用原生的 RestHighLevelClient 用法来实现。使用Easy-Es来操作ES确实足够优雅,它类似MyBatis-Plus的用法能大大降低我们的学习成本

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

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

相关文章

【Tomcat与网络3】Tomcat的整体架构

目录 1.演进1&#xff1a;将连接和处理服务分开 2演进2&#xff1a;Container的演进 3 再论Tomcat的容器结构 4 Tomcat处理请求的过程 5 请求的处理过程与Pipeline-Valve管道 在前面我们介绍了Servlet的基本原理&#xff0c;本文我们结合Tomcat来分析一下如何设计一个大型…

Cache Lab:Part A【模拟出使用LRU策略的高速缓存存储器组织结构】

目录 任务描述 知识回顾 实验内容 测试结果 Cache Lab 对应《CS:APP》6.3节至第六章结束的内容。 任务描述 Your job for Part A is to fill in the csim.c file so that it takes the same command line arguments and produces the identical output as the reference …

[NCTF2019]Fake XML cookbook(特详解)

先试了一下弱口令&#xff0c;哈哈习惯了 查看页面源码发现xml function doLogin(){var username $("#username").val();var password $("#password").val();if(username "" || password ""){alert("Please enter the usern…

基于大数据的B站数据分析系统的设计与实现

摘要&#xff1a;随着B站&#xff08;哔哩哔哩网&#xff09;在国内视频分享平台的崛起&#xff0c;用户规模和数据量不断增加。为了更好地理解和利用这些海量的B站数据&#xff0c;设计并实现了一套基于Python的B站数据分析系统。该系统采用了layui作为前端框架、Flask作为后端…

代码随想录算法训练营29期|day35 任务以及具体任务

860.柠檬水找零 class Solution {public boolean lemonadeChange(int[] bills) {int five 0;int ten 0;for (int i 0; i < bills.length; i) {if (bills[i] 5) {five;} else if (bills[i] 10) {five--;ten;} else if (bills[i] 20) {if (ten > 0) {ten--;five--;} …

242. 有效的字母异位词(力扣)(C语言题解)

✨欢迎来到脑子不好的小菜鸟的文章✨ &#x1f388;创作不易&#xff0c;麻烦点点赞哦&#x1f388; 所属专栏&#xff1a;刷题 我的主页&#xff1a;脑子不好的小菜鸟 文章特点&#xff1a;关键点和步骤讲解放在 代码相应位置 题目链接&#xff1a; 242. 有效的字母异位词 …

玻璃封装高温烧结航空插头插座连接器

概述 随着风电行业深入发展&#xff0c;风力发电机组使用的传感器主要有:位置传感器、加速度传感器、压力传感器、温度传感器、液位传感器、电压电流互感器、压点薄膜传感器等。对电子元器件的性能提出了更进一步的要求。连接器作为连接各个电子元器件的血脉&#xff0c;在保持…

萝卜视频源码前后端带视频演示

萝卜影视源码前端是用JAVA开发的全原生APP源码&#xff0c;后端用的是二次开发的苹果CMS&#xff0c;支持局域网投屏&#xff0c;视频软解硬解&#xff0c;播放器自带弹幕功能。支持解析官方视频&#xff0c;支持M3U8&#xff0c;MP4。 开屏广告&#xff0c;全局广告&#xff0…

Unity3D正则表达式的使用

系列文章目录 unity工具 文章目录 系列文章目录前言一、匹配正整数的使用方法1-1、代码如下1-2、结果如下 二、匹配大写字母2-1、代码如下1-2、结果如下 三、Regex类3-1、Match&#xff08;&#xff09;3-2、Matches()3-3、IsMatch&#xff08;&#xff09; 四、定义正则表达式…

【测试运维】接口测试各知识md文档学习笔记第1篇(已分享,附代码)

本系列文章md笔记&#xff08;已分享&#xff09;主要讨论接口测试相关知识。目标&#xff1a;了解接口测试服务对象&#xff0c;基本作用&#xff0c;接口测试环境插件工具&#xff0c;掌握jmeter的使用&#xff0c;掌握接口测试的测试用例编写。熟悉Jmeter工具组成&#xff0…

数据的绘画:数据可视化为我们打开信息的画卷

在迅猛发展的大数据时代&#xff0c;数据可视化成为我们逐步适应信息激增的得力工具。通过直观展示庞大复杂的数据&#xff0c;数据可视化不仅简化了信息的理解&#xff0c;更为我们提供了深入洞察的机会。这一技术的崛起不仅仅是技术的进步&#xff0c;更是对我们信息处理方式…

C++_list

目录 一、模拟实现list 1、list的基本结构 2、迭代器封装 2.1 正向迭代器 2.2 反向迭代器 3、指定位置插入 4、指定位置删除 5、结语 前言&#xff1a; list是STL(标准模板库)中的八大容器之一&#xff0c;而STL属于C标准库的一部分&#xff0c;因此在C中可以直接使用…

04MARL - priori kownledge and challenge

文章目录 一、General Learning Process二、中心化学习与独立学习1.central learning1.1 CQL1.2 局限性 2.Independent Learning2.1 IQL2.2 局限性 三、MARL挑战1.非平稳性1.1单智能体强化学习的非平稳性1.2 MARL非平稳性 2.信用分配问题3.均衡选择4.拓展性 四、协作型MARL的模…

Web实战丨基于Django的简单网页计数器

文章目录 写在前面Django简介主要程序运行结果系列文章写在后面 写在前面 本期内容 基于django的简单网页计数器 所需环境 pythonpycharm或vscodedjango 下载地址 https://download.csdn.net/download/m0_68111267/88795604 Django简介 Django 是一个用 Python 编写的高…

MySQL的原生API实现插入数据后在可视化工具上不显示的问题解决

显示表中有两行数据&#xff0c;该表也设置了主键和唯一索引 点进表里看却没有数据 问题原因出现在这里&#xff0c;虽然很多常用的数据库连接池都会开启自动提交&#xff0c;但ibatis的SqlSession使用sessionFactory.openSession()创建时&#xff0c;默认的自动提交是false&am…

纯静态微信小程序水果商城

首页代码 <view class"container"><!-- 轮播图 --><view class"swiper-container"><swiper class"screen-swiper" indicator-dots"true" circular"true" autoplay"true" interval"300…

数据结构——栈和队列(C语言)

栈种常见的数据结构&#xff0c;它用来解决一些数据类型的问题&#xff0c;那么好&#xff0c;我来带着大家来学习一下栈 文章目录 栈对栈的认识栈的模拟实现栈的练习方法一方法二 栈 对栈的认识 栈&#xff08;stack&#xff09;是限定只能在表的一端进行插入删除操作的线性…

VxTerm:SSH工具中的中文显示和乱码时的相关信息和一些基本的知识

当我们写的程序含有控制台(Console)输出时&#xff0c;如果输入内容包含中文时&#xff0c;我们一般需要知道下面的信息&#xff0c;才能正确的搞清楚怎么处理中文显示的问题&#xff1a; 1、实际程序或文件中的实际编码&#xff1a; Linux下的应用程序和文本文件&#xff0c;…

系统架构设计师-21年-下午题目

系统架构设计师-21年-下午题目 更多软考知识请访问 https://ruankao.blog.csdn.net/ 试题一必答&#xff0c;二、三、四、五题中任选两题作答 试题一 (25分) 说明 某公司拟开发一套机器学习应用开发平台&#xff0c;支持用户使用浏览器在线进行基于机器学习的智能应用开发…

matlab appdesigner系列-仪器仪表3-旋钮

旋钮&#xff0c;同过旋转显示特定的值 示例&#xff1a;模拟收音机调频 操作步骤&#xff1a; 1&#xff09;将旋钮、标签按钮拖拽到画布上&#xff0c;将标签文字修改为&#xff1a;欢迎收听&#xff0c;并将旋钮其数值范围改为90-107 2&#xff09;设置旋钮的回调函数 代…