- 关于String.format
ruan114514
java开发语言
在Java开发中,我们经常需要处理字符串拼接——比如生成日志、格式化用户输出、拼接订单号或二维码ID。你可能遇到过这样的代码:Stringlog="用户"+username+"在"+newSimpleDateFormat("yyyy-MM-ddHH:mm:ss").format(newDate())+"登录,IP地址是"+ip;这种手动拼接的方式不仅代码冗长,还容易出现格式错误(比如日期格式遗漏、
- C#字符串格式化之$语法
码农浩克
c#开发语言数据库
引言字符串是编程中使用较广的一种数据,它由数字、字母、下划线等组成。在使用过程中会对字符串进行格式化。在C#语言中,.NET6及以上使用字符串插值($""语法)对字符串格式化。$语法.NET6及以上提供的一种新的语法糖,它的作用相当于对String.format的简化。使用$可以将字符串字面量标识为内插字符串,内插字符串将可设置其格式。语法结构1、语法格式如下:$("{[,][:]}")2、语法说
- Process.Start 方法 (String, String)参数本身带有空格的解决方法
项目中自动更新的时候,需要启动一个单独的更新的组件,使用的是Process.Start方法,开始的时候测试没有问题,安装客户机的时候,启动的时候程序出错。调试之后发现安装的是“C:\ProgramFiles****”,ProgramFiles中间的空格被认为成了参数的分隔符。经网上查找找到解决方案如下:将每个路径字符串用引号引起来。stringarg=string.Format("\"{0}\"\
- C#格式化输出
SJ6688
C#专栏c#开发语言
C#提供了多个格式化输出的方法,使得我们在灵活且可读的方法构建字符串;主要的格式化方法包括:String.Format方法、字符串插值,以及使用符合格式字符串与Console.WriteLint或Console.Write函数。String.Format方法string.Format是一种传统且强大的方法,用于创建格式化的字符串。它可以接受模板字符串和一系列参数,然后根据模板中的占位符{N,M}来
- Java消息自定义模板
LiuKouvu
Java基础javaspringspringboot
Java消息自定义模板前言一、String.format的使用1.代码眼见为实二、String.replaceAll的使用1.话不多说撸代码三、用工具类1.看例子四、用正则五、Java利用MessageFormat实现短信模板的匹配前言在我们开发的过程中,必定回遇到这样或那样的消息发送,统一的模板,统一消息发送方式能避免我们不停的造轮子,使我们的代码既美观有又比较好的扩展性一、String.for
- Python字符串格式化(一):三种经典格式化方法
dudly
python开发语言
文章目录一、%operator:C语言风格的初代格式化方案(Python2.0引入)1.语法核心:占位符与类型码2.进阶用法:格式修饰符3.致命缺陷:类型严格匹配的陷阱4.适用场景:旧代码维护的兼容性选择二、string.format():面向对象的格式化革命(Python2.6引入)1.语法升级:从占位符到表达式引擎2.格式说明符:精细化控制的瑞士军刀(1)对齐与填充(2)数值格式(3)日期时间
- int值转换为时间(data)
A富得流油的咸鸭蛋
在开发中时常会遇到后台返回给自己一个值,但并不是data格式,需要我们自己来转换,我把我用的方法介绍给大家。intlength=1200;(后台返回的数值)Stringtime;if(length<3600){time=String.format("%1$02d:%2$02d",length/60,length%60);}else{time=String.format("%1$d:%2$02d:%
- java.util.MissingFormatArgumentException: Format specifier %E9%9B%A8%E6%B1%A1
唔66
解析出错问题java.util.MissingFormatArgumentException:Formatspecifier‘%E’解读String.format(decodeStr,args)解析的String存在%E9%9B%A8%E6%B1%A1就会报错最简单的方法是是将整个string放在里面转成带有汉字或其他字符就不会报错【%上网查询是占位符】,后面没有替换的字符导致报错解决办法先str
- C#学习之旅--Day02-占位符-运算符-数据类型转换-选择语句
秦果
c#学习开发语言
一、占位符1、对字符串中占位使用string.Format,"",即可实现stringgunName="AK47";stringneCapacity="30";stringstr=string.Format("枪的名称为:{0},容量为:{1}",gunName,neCapacity);Console.WriteLine(str);2、{0:c}显示货币10.00Console.WriteLine
- C# DataTable 导出CSV 文件并在客户端下载
茶暖人凉
c#excel
publicstaticboolExportToCSV(System.Data.DataTabledt){stringstrLine="";stringpathFile=String.Format("{0}{1}.csv",HttpContext.Current.Server.MapPath("Excel/"),"客户列表");//文件保存路径及名称FileInfofi=newFileInfo(p
- JDK17新特性
yiyi5656
java开发语言
一、语法层面新特性1、文本块文本块指多行的字符串,使用连续的三个双引号来包围一段带换行的文字,它避免了换行转义的需要,并支持String.format。同时添加了两个新的转义字符::,置于行尾,用来将两行连接为一行\s:单个空白字符2、Switch表达式增强支持表达式,增加yield关键字,跳出switch并返回结果3、instanceof的模式匹配4、var局部变量推导二、模块化及类封装1、记录
- double保留两位小数的方法
Y_L_Lee
工作笔记java
方法1(四舍五入,返回值是一个字符串)DecimalFormatdecimalFormat=newDecimalFormat("0.00");Stringformat=decimalFormat.format(5.3687545);方法2(四舍五入,返回值是一个字符串)Stringformat=String.format("%.2f",5.3687545);方法3(返回值是double,UP向上取
- double保留2位小数
卑微远
数据类型double保留小数点位数
1.formatdoubledou=3.14789;StringdouStr=String.format("%.2f",dou);System.out.println("douStr:"+douStr);注:四舍五入,位数不够则会用0补齐。2.bigDecimaldoubledou=3.14789;//BigDecimal.ROUND_UP四舍五入//BigDecimal.ROUND_DOWN直接
- double保留两位小数的四种方法
小小野猪
Java基础javadouble
这里写目录标题引言方法一:使用`BigDecimal`类方法二:使用`DecimalFormat`类方法三:使用`NumberFormat`类方法四:使用`String.format`方法结论声明引言在Java编程中,我们经常遇到需要对double类型的浮点数进行精确截断或四舍五入保留两位小数的需求。由于double类型在进行浮点运算时存在精度问题,因此,为了获得期望的精确表示,我们可以采用一些专
- 一篇文章让你学会Java之格式化输出
凭君语未可
Javajava开发语言
这里写目录标题一、格式化输出方法1.使用`String.format()`方法语法:示例:2.使用`System.out.printf()`方法语法:示例:3.使用`Formatter`类示例:代码分析:二、常见的格式说明符:1.整数类型格式化说明符2.浮点类型格式化说明符3.字符串格式化说明符4.日期和时间格式化说明符5.百分号格式化说明符6.其他格式化控制符三、常用的格式化选项:1.宽度(Wi
- Lua毫秒时间-判断操作间隔(如点击按钮)
hookby
lua开发语言
--需要luajitself.lastClickTime=self.clickedTimeoros.time()localmSecTime=tonumber(string.format("%d.%03d",math.floor(sec),msec*1000))self.clickedTime=mSecTimeself.clickInterval=self.clickedTime-self.last
- Lua语法(一)
monGyrate
Lua语言lua开发语言
参考链接:系列链接:Lua语法(一)系列链接:Lua语法(二)系列链接:Lua语法(三)——元表与元方法系列链接:Lua语法(四)——协程系列链接:Lua语法(五)——垃圾回收系列链接:Lua语法(六)——面相对象编程Lua语法目录简介正文语言基础一、语法规范二、类型和值三、数值运算数学库随机数lua数值表示范围四、字符串字符串库string.sub截取一段string.format格式化字符串s
- 蓝易云 - 介绍String.format()方法中的格式占位符用法。
蓝易云
python开发语言vue.jshttp前端kuberneteslinux
String.format()方法是Java中一种用于创建格式化字符串的强大工具,该方法通过占位符和参数的结合使用,可以控制字符串中数据的呈现方式。以下是一些最常用的格式占位符及其用法说明:%s-字符串格式占位符:用于插入一个字符串,替换时会调用对象的toString()方法。%d-整数格式占位符:用于插入十进制整数。%f-浮点数格式占位符:用于插入十进制浮点数。可以指定小数点后的位数。%t-日期
- String.format()详细用法
简单的绿竹
.net(C#)基础知识c#
String类有一个强大的字符串格式化方法format()。下面是常用的方法总结。一、占位符类型Stringformatted=String.format("%s今年%d岁。","小李",25);//"小李今年25岁。"二、字符串和整数格式化//将第二个入参拼接到模板中,入参长度如果不足10左侧用空格补齐,超过10全量输出System.out.println(String.format("%10s
- C#字符串格式化
weixin_42579159
c#
String.Format方法的几种定义:String.Format(String,Object)将指定的String中的格式项替换为指定的Object实例的值的文本等效项。String.Format(String,Object[])将指定String中的格式项替换为指定数组中相应Object实例的值的文本等效项。String.Format(IFormatProvider,String,Objec
- string.Format对C#字符串格式化
星辰逸风
c#
string.Format对C#字符串格式化String.Format方法的几种定义:String.Format(String,Object)将指定的String中的格式项替换为指定的Object实例的值的文本等效项。String.Format(String,Object[])将指定String中的格式项替换为指定数组中相应Object实例的值的文本等效项。String.Format(IForma
- C#格式化字符串中输入花括号
gc_2299
dotnet编程C#格式化字符串花括号
一直都在使用String.Format函数格式化输出字符串,但从来没有在其中输出过带花括号的字符串,花括号一般在String.Format的格式化字符串中指定输出项及输出项的格式,如果要将其作为普通文本内容输出,还得试试才行,以输出“{test}”为例进行测试。 首先想到的是用’\‘转义,一般特殊字符都是这么干的,直接使用string.Format(“{{0}}”,“test”)语句,结果程
- C# 字符串格式化
简单的绿竹
基础知识.net(C#)c#
https://blog.csdn.net/shengchang82/article/details/46821121、格式化货币(跟系统的环境有关,中文系统默认格式化人民币,英文系统格式化美元)string.Format("{0:C}",0.2)结果为:¥0.20(英文操作系统结果:$0.20)默认格式化小数点后面保留两位小数,如果需要保留一位或者更多,可以指定位数string.Format("
- Java int转String位数不足左补0(共12位)
珠光
代码string
方法一:sendXmlLen=String.format("%012d",sendXmlStr.length());方法二:StringBuilderlengthStr=newStringBuilder(Objects.toString(sendXmlStr.length()));intlength=lengthStr.length();if(length<12){intcount=12-leng
- Java中格式化字符串的方法(整理后的)
满脑子灵感
Java基础格式化Java
一、String.format方法:1.整数进行格式化:%[index$][标识][最小宽度]转换方式标识:-在最小宽度内左对齐,只适十进制,每3位数之间用','分隔转换方式:d十进制o八进制x或X十六进制(注:%与转换方式必须有,不能省略)2.浮点数格式化:%[index$][标识][最小宽度][.精度]转化方式转换方式:f十进制普通表示g或G自动普通或科学计数方式(注:index$表,参数的位
- Android String.format() 引发的卡顿问题
wk灬丨
性能优化android
String.format()是Java中用于创建格式化字符串的方法,Android作为基于Java的平台,同样提供了这个功能。这个方法允许我们构建一个带有占位符的字符串,然后将这些占位符替换为具体的值。String.format()方法的用法与printf()在C语言中的用法十分相似。我们可以指定字符串中的每一个占位符的格式,比如:整数、浮点数、字符串等,然后通过String.format()的
- C#的String.Format 方法
wenchm
c#java前端
目录一、重载二、Format(String,Object)1.定义2.示例三、Format(String,Object[])1.定义2.示例3.示例将对象的值转换为基于指定格式的字符串,并将其插入到另一个字符串。一、重载Format(IFormatProvider,String,Object,Object,Object)将字符串中的格式项替换为三个指定对象的字符串表示形式。参数提供区域性特定的格式
- Unity Xlua打包后 找不到lua脚本
DDSDQPMZ
Unityluaunity开发语言
UnityXlua打包后找不到lua脚本如果是使用下面这种方式的,看看路径中是否包含中文luaEnv.DoString(string.Format("package.path='{0}/Lua/?.lua'",Application.streamingAssetsPath));建议自己创建CustomLoader代码如下:privatevoidStart(){luaEnv=newLuaEnv();
- Android动态字符串拼接----%s
aiyagp14944
移动开发
在开发经常遇到字符串中的某一数据或多个数据是动态变化的。如下图不要创建3个TextView,暂时不考虑颜色变化的情况,可以用以下做法。您的车辆距下次保养还有%sKM\n下次保养建议更换空调滤芯\n是否为您预约车辆保养在代码中调用:Stringtitle=String.format(getResources().getString(R.string.maintain_msg),"999");两个或者
- C# 读写INI文件中文乱码问题
道阻且长丶
C#c#
C#读写INI文件中文乱码问题INIUtil操作类常见的读取ini文件的方式INIUtil操作类//ini文件staticstringIniFileName=string.Format(@"{0}\{1}.ini",Application.StartupPath,Application.ProductName);[DllImport("kernel32.dll")]privatestaticext
- 算法 单链的创建与删除
换个号韩国红果果
c算法
先创建结构体
struct student {
int data;
//int tag;//标记这是第几个
struct student *next;
};
// addone 用于将一个数插入已从小到大排好序的链中
struct student *addone(struct student *h,int x){
if(h==NULL) //??????
- 《大型网站系统与Java中间件实践》第2章读后感
白糖_
java中间件
断断续续花了两天时间试读了《大型网站系统与Java中间件实践》的第2章,这章总述了从一个小型单机构建的网站发展到大型网站的演化过程---整个过程会遇到很多困难,但每一个屏障都会有解决方案,最终就是依靠这些个解决方案汇聚到一起组成了一个健壮稳定高效的大型系统。
看完整章内容,
- zeus持久层spring事务单元测试
deng520159
javaDAOspringjdbc
今天把zeus事务单元测试放出来,让大家指出他的毛病,
1.ZeusTransactionTest.java 单元测试
package com.dengliang.zeus.webdemo.test;
import java.util.ArrayList;
import java.util.List;
import org.junit.Test;
import
- Rss 订阅 开发
周凡杨
htmlxml订阅rss规范
RSS是 Really Simple Syndication的缩写(对rss2.0而言,是这三个词的缩写,对rss1.0而言则是RDF Site Summary的缩写,1.0与2.0走的是两个体系)。
RSS
- 分页查询实现
g21121
分页查询
在查询列表时我们常常会用到分页,分页的好处就是减少数据交换,每次查询一定数量减少数据库压力等等。
按实现形式分前台分页和服务器分页:
前台分页就是一次查询出所有记录,在页面中用js进行虚拟分页,这种形式在数据量较小时优势比较明显,一次加载就不必再访问服务器了,但当数据量较大时会对页面造成压力,传输速度也会大幅下降。
服务器分页就是每次请求相同数量记录,按一定规则排序,每次取一定序号直接的数据
- spring jms异步消息处理
510888780
jms
spring JMS对于异步消息处理基本上只需配置下就能进行高效的处理。其核心就是消息侦听器容器,常用的类就是DefaultMessageListenerContainer。该容器可配置侦听器的并发数量,以及配合MessageListenerAdapter使用消息驱动POJO进行消息处理。且消息驱动POJO是放入TaskExecutor中进行处理,进一步提高性能,减少侦听器的阻塞。具体配置如下:
- highCharts柱状图
布衣凌宇
hightCharts柱图
第一步:导入 exporting.js,grid.js,highcharts.js;第二步:写controller
@Controller@RequestMapping(value="${adminPath}/statistick")public class StatistickController { private UserServi
- 我的spring学习笔记2-IoC(反向控制 依赖注入)
aijuans
springmvcSpring 教程spring3 教程Spring 入门
IoC(反向控制 依赖注入)这是Spring提出来了,这也是Spring一大特色。这里我不用多说,我们看Spring教程就可以了解。当然我们不用Spring也可以用IoC,下面我将介绍不用Spring的IoC。
IoC不是框架,她是java的技术,如今大多数轻量级的容器都会用到IoC技术。这里我就用一个例子来说明:
如:程序中有 Mysql.calss 、Oracle.class 、SqlSe
- TLS java简单实现
antlove
javasslkeystoretlssecure
1. SSLServer.java
package ssl;
import java.io.FileInputStream;
import java.io.InputStream;
import java.net.ServerSocket;
import java.net.Socket;
import java.security.KeyStore;
import
- Zip解压压缩文件
百合不是茶
Zip格式解压Zip流的使用文件解压
ZIP文件的解压缩实质上就是从输入流中读取数据。Java.util.zip包提供了类ZipInputStream来读取ZIP文件,下面的代码段创建了一个输入流来读取ZIP格式的文件;
ZipInputStream in = new ZipInputStream(new FileInputStream(zipFileName));
&n
- underscore.js 学习(一)
bijian1013
JavaScriptunderscore
工作中需要用到underscore.js,发现这是一个包括了很多基本功能函数的js库,里面有很多实用的函数。而且它没有扩展 javascript的原生对象。主要涉及对Collection、Object、Array、Function的操作。 学
- java jvm常用命令工具——jstatd命令(Java Statistics Monitoring Daemon)
bijian1013
javajvmjstatd
1.介绍
jstatd是一个基于RMI(Remove Method Invocation)的服务程序,它用于监控基于HotSpot的JVM中资源的创建及销毁,并且提供了一个远程接口允许远程的监控工具连接到本地的JVM执行命令。
jstatd是基于RMI的,所以在运行jstatd的服务
- 【Spring框架三】Spring常用注解之Transactional
bit1129
transactional
Spring可以通过注解@Transactional来为业务逻辑层的方法(调用DAO完成持久化动作)添加事务能力,如下是@Transactional注解的定义:
/*
* Copyright 2002-2010 the original author or authors.
*
* Licensed under the Apache License, Version
- 我(程序员)的前进方向
bitray
程序员
作为一个普通的程序员,我一直游走在java语言中,java也确实让我有了很多的体会.不过随着学习的深入,java语言的新技术产生的越来越多,从最初期的javase,我逐渐开始转变到ssh,ssi,这种主流的码农,.过了几天为了解决新问题,webservice的大旗也被我祭出来了,又过了些日子jms架构的activemq也开始必须学习了.再后来开始了一系列技术学习,osgi,restful.....
- nginx lua开发经验总结
ronin47
使用nginx lua已经两三个月了,项目接开发完毕了,这几天准备上线并且跟高德地图对接。回顾下来lua在项目中占得必中还是比较大的,跟PHP的占比差不多持平了,因此在开发中遇到一些问题备忘一下 1:content_by_lua中代码容量有限制,一般不要写太多代码,正常编写代码一般在100行左右(具体容量没有细心测哈哈,在4kb左右),如果超出了则重启nginx的时候会报 too long pa
- java-66-用递归颠倒一个栈。例如输入栈{1,2,3,4,5},1在栈顶。颠倒之后的栈为{5,4,3,2,1},5处在栈顶
bylijinnan
java
import java.util.Stack;
public class ReverseStackRecursive {
/**
* Q 66.颠倒栈。
* 题目:用递归颠倒一个栈。例如输入栈{1,2,3,4,5},1在栈顶。
* 颠倒之后的栈为{5,4,3,2,1},5处在栈顶。
*1. Pop the top element
*2. Revers
- 正确理解Linux内存占用过高的问题
cfyme
linux
Linux开机后,使用top命令查看,4G物理内存发现已使用的多大3.2G,占用率高达80%以上:
Mem: 3889836k total, 3341868k used, 547968k free, 286044k buffers
Swap: 6127608k total,&nb
- [JWFD开源工作流]当前流程引擎设计的一个急需解决的问题
comsci
工作流
当我们的流程引擎进入IRC阶段的时候,当循环反馈模型出现之后,每次循环都会导致一大堆节点内存数据残留在系统内存中,循环的次数越多,这些残留数据将导致系统内存溢出,并使得引擎崩溃。。。。。。
而解决办法就是利用汇编语言或者其它系统编程语言,在引擎运行时,把这些残留数据清除掉。
- 自定义类的equals函数
dai_lm
equals
仅作笔记使用
public class VectorQueue {
private final Vector<VectorItem> queue;
private class VectorItem {
private final Object item;
private final int quantity;
public VectorI
- Linux下安装R语言
datageek
R语言 linux
命令如下:sudo gedit /etc/apt/sources.list1、deb http://mirrors.ustc.edu.cn/CRAN/bin/linux/ubuntu/ precise/ 2、deb http://dk.archive.ubuntu.com/ubuntu hardy universesudo apt-key adv --keyserver ke
- 如何修改mysql 并发数(连接数)最大值
dcj3sjt126com
mysql
MySQL的连接数最大值跟MySQL没关系,主要看系统和业务逻辑了
方法一:进入MYSQL安装目录 打开MYSQL配置文件 my.ini 或 my.cnf查找 max_connections=100 修改为 max_connections=1000 服务里重起MYSQL即可
方法二:MySQL的最大连接数默认是100客户端登录:mysql -uusername -ppass
- 单一功能原则
dcj3sjt126com
面向对象的程序设计软件设计编程原则
单一功能原则[
编辑]
SOLID 原则
单一功能原则
开闭原则
Liskov代换原则
接口隔离原则
依赖反转原则
查
论
编
在面向对象编程领域中,单一功能原则(Single responsibility principle)规定每个类都应该有
- POJO、VO和JavaBean区别和联系
fanmingxing
VOPOJOjavabean
POJO和JavaBean是我们常见的两个关键字,一般容易混淆,POJO全称是Plain Ordinary Java Object / Plain Old Java Object,中文可以翻译成:普通Java类,具有一部分getter/setter方法的那种类就可以称作POJO,但是JavaBean则比POJO复杂很多,JavaBean是一种组件技术,就好像你做了一个扳子,而这个扳子会在很多地方被
- SpringSecurity3.X--LDAP:AD配置
hanqunfeng
SpringSecurity
前面介绍过基于本地数据库验证的方式,参考http://hanqunfeng.iteye.com/blog/1155226,这里说一下如何修改为使用AD进行身份验证【只对用户名和密码进行验证,权限依旧存储在本地数据库中】。
将配置文件中的如下部分删除:
<!-- 认证管理器,使用自定义的UserDetailsService,并对密码采用md5加密-->
- mac mysql 修改密码
IXHONG
mysql
$ sudo /usr/local/mysql/bin/mysqld_safe –user=root & //启动MySQL(也可以通过偏好设置面板来启动)$ sudo /usr/local/mysql/bin/mysqladmin -uroot password yourpassword //设置MySQL密码(注意,这是第一次MySQL密码为空的时候的设置命令,如果是修改密码,还需在-
- 设计模式--抽象工厂模式
kerryg
设计模式
抽象工厂模式:
工厂模式有一个问题就是,类的创建依赖于工厂类,也就是说,如果想要拓展程序,必须对工厂类进行修改,这违背了闭包原则。我们采用抽象工厂模式,创建多个工厂类,这样一旦需要增加新的功能,直接增加新的工厂类就可以了,不需要修改之前的代码。
总结:这个模式的好处就是,如果想增加一个功能,就需要做一个实现类,
- 评"高中女生军训期跳楼”
nannan408
首先,先抛出我的观点,各位看官少点砖头。那就是,中国的差异化教育必须做起来。
孔圣人有云:有教无类。不同类型的人,都应该有对应的教育方法。目前中国的一体化教育,不知道已经扼杀了多少创造性人才。我们出不了爱迪生,出不了爱因斯坦,很大原因,是我们的培养思路错了,我们是第一要“顺从”。如果不顺从,我们的学校,就会用各种方法,罚站,罚写作业,各种罚。军
- scala如何读取和写入文件内容?
qindongliang1922
javajvmscala
直接看如下代码:
package file
import java.io.RandomAccessFile
import java.nio.charset.Charset
import scala.io.Source
import scala.reflect.io.{File, Path}
/**
* Created by qindongliang on 2015/
- C语言算法之百元买百鸡
qiufeihu
c算法
中国古代数学家张丘建在他的《算经》中提出了一个著名的“百钱买百鸡问题”,鸡翁一,值钱五,鸡母一,值钱三,鸡雏三,值钱一,百钱买百鸡,问翁,母,雏各几何?
代码如下:
#include <stdio.h>
int main()
{
int cock,hen,chick; /*定义变量为基本整型*/
for(coc
- Hadoop集群安全性:Hadoop中Namenode单点故障的解决方案及详细介绍AvatarNode
wyz2009107220
NameNode
正如大家所知,NameNode在Hadoop系统中存在单点故障问题,这个对于标榜高可用性的Hadoop来说一直是个软肋。本文讨论一下为了解决这个问题而存在的几个solution。
1. Secondary NameNode
原理:Secondary NN会定期的从NN中读取editlog,与自己存储的Image进行合并形成新的metadata image
优点:Hadoop较早的版本都自带,