jbase实现通用码表
没有通用码表的体系是不完美的,当年我用C#能实现的通用码表,现在在java一样的实现了,通用码表对提高开发效率和降低开发成本的作用巨大,开发可以专注写业务,而不必被太多的维护界面束缚。进而体现在产品竞争力上面,别人还是花大量时间做维护界面,我们建表了就有码表维护界面,只需要做特殊的维护界面(还是基于代码生成的基础组装)
通用码表原理看这里
通用码表离不开自己实现ORM,通过ORM解析实体的外键参照信息组装带外键列的查询,这样子表界面参照的父表名称才能显示名称而不是主键。
FK实现实例,没有实体的外键特性和ORM的底层支持,码表都是无稽之谈
/*** 码表查询,不分页** @param modelName 实体名称* @param param 查询条件参数,数据列名和值的键对* @param orderField 排序字段,如RowID Desc* @param returnCount 是否输出数据总行数* @param fields 显示字段,为空显示所有列,字段名称以英文','隔开,如:RowID,Code,Name* @param joiner 连接符,为空或不给则查询条件以且连接,给的话长度比参数少1* @param operators 操作符,为空或不给的话条件以等来判断,给的话与参数长度一致。如!=,<,>* @return*/@Overridepublic String QueryAllWithFKByName(String modelName, List<ParamDto> param, String orderField, boolean returnCount, String fields, List<String> joiner, List<String> operators) throws Exception {return QueryAllWithFKByName(modelName, param, orderField, returnCount, -1, -1, fields, joiner, operators);}/*** 根据条件+字段查询,查询结果按指定的页面把数据按JSON返回;* 该方法会把外键关联的字段查出来,用来取缔试图的查询** @param model 实体对象* @param param 查询条件参数,数据列名和值的键对* @param orderFields 排序字段,如RowID Desc* @param returnCount 是否输出数据总行数* @param pageSize 页大小。为-1,无条件查所有数据* @param pageIndex 第几页。为-1,无条件查询所有数据* @param fields 显示字段,为空显示所有列,字段名称以英文','隔开,如:RowID,Code,Name* @param joiner 连接符,为空或不给则查询条件以且连接,给的话长度比参数少1* @param operators 操作符,为空或不给的话条件以等来判断,给的话与参数长度一致。如!=,<,>* @param <T> 限定实体类型* @return 查询json串*/@Overridepublic <T> String QueryAllWithFK(T model, HashParam param, String orderFields, boolean returnCount, int pageSize, int pageIndex, String fields, List<String> joiner, List<String> operators) throws Exception {List<ParamDto> pdto = null;if (param != null) {pdto = param.GetParam();}return QueryAllWithFK(model, pdto, orderFields, returnCount, pageSize, pageIndex, fields, joiner, operators);}/*** 根据条件+字段查询,查询结果按指定的页面把数据按JSON返回;* 该方法会把外键关联的字段查出来,用来取缔试图的查询* 不分页** @param model 实体对象* @param param 查询条件参数,数据列名和值的键对* @param orderFields 排序字段,如RowID Desc* @param returnCount 是否输出数据总行数* @param fields 显示字段,为空显示所有列,字段名称以英文','隔开,如:RowID,Code,Name* @param joiner 连接符,为空或不给则查询条件以且连接,给的话长度比参数少1* @param operators 操作符,为空或不给的话条件以等来判断,给的话与参数长度一致。如!=,<,>* @param <T> 限定实体类型* @return 查询json串*/@Overridepublic <T> String QueryAllWithFK(T model, HashParam param, String orderFields, boolean returnCount, String fields, List<String> joiner, List<String> operators) throws Exception {List<ParamDto> pdto = null;if (param != null) {pdto = param.GetParam();}return QueryAllWithFK(model, pdto, orderFields, returnCount, fields, joiner, operators);}/*** 根据条件+字段查询,查询结果按指定的页面把数据按JSON返回;* 该方法会把外键关联的字段查出来,用来取缔试图的查询* 不分页** @param model 实体对象* @param param 查询条件参数,数据列名和值的键对* @param orderFields 排序字段,如RowID Desc* @param returnCount 是否输出数据总行数* @param fields 显示字段,为空显示所有列,字段名称以英文','隔开,如:RowID,Code,Name* @param joiner 连接符,为空或不给则查询条件以且连接,给的话长度比参数少1* @param operators 操作符,为空或不给的话条件以等来判断,给的话与参数长度一致。如!=,<,>* @param <T> 限定实体类型* @return 查询json串*/@Overridepublic <T> String QueryAllWithFK(T model, List<ParamDto> param, String orderFields, boolean returnCount, String fields, List<String> joiner, List<String> operators) throws Exception {return QueryAllWithFK(model, param, orderFields, returnCount, -1, -1, fields, joiner, operators);}/*** 根据条件+字段查询,查询结果按指定的页面把数据按JSON返回;* 该方法会把外键关联的字段查出来,用来取缔试图的查询** @param model 实体对象* @param param 查询条件参数,数据列名和值的键对* @param orderFields 排序字段,如RowID Desc* @param returnCount 是否输出数据总行数* @param pageSize 页大小。为-1,无条件查所有数据* @param pageIndex 第几页。为-1,无条件查询所有数据* @param fields 显示字段,为空显示所有列,字段名称以英文','隔开,如:RowID,Code,Name* @param joiner 连接符,为空或不给则查询条件以且连接,给的话长度比参数少1* @param operators 操作符,为空或不给的话条件以等来判断,给的话与参数长度一致。如!=,<,>* @param <T> 限定实体类型* @return 查询json串*/@Overridepublic <T> String QueryAllWithFK(T model, List<ParamDto> param, String orderFields, boolean returnCount, int pageSize, int pageIndex, String fields, List<String> joiner, List<String> operators) throws Exception {//json数据组装容器StringBuilder jsonsb = new StringBuilder();//查询起始行数int fromRow = -1;//查询结束行数int toRow = -1;//是否查询全部数据boolean findAll = false;//记录总行数int rowCount = 0;if (fields != null && !fields.isEmpty()) {fields = "," + fields + ",";}//如果未传入分页数据其中一个未-1,则认为部分页而查询所有数据if (pageIndex == -1 || pageSize == -1) {findAll = true;}//计算查询起始和结束行数else {fromRow = (pageIndex - 1) * pageSize;toRow = pageIndex * pageSize;}PreparedStatement pstat = null;ResultSet rst = null;LIS.DAL.ORM.Common.TableInfo tableInfo = LIS.DAL.ORM.Common.ModelToSqlUtil.GetTypeInfo(model);//根据表信息将查询参数组装成Select SQLString sql = LIS.DAL.ORM.Common.ModelToSqlUtil.GetSelectSqlByTableInfo(Manager().GetIDbFactory(factoryName), tableInfo, param, operators, joiner, orderFields, true, -1);//写SQL日志LIS.Core.Util.LogUtils.WriteSqlLog("执行QueryAllWithFK返回String查询SQL:" + sql);//如果返回总行数,返回总行数写法if (returnCount) {jsonsb.append("{");jsonsb.append("\"rows\":[");}//否则采用普通数组写法else {jsonsb.append("[");}StringBuilder rowAllsb = new StringBuilder();try {pstat = Manager().Connection().prepareStatement(sql);String paraSql = DBParaUtil.SetDBPara(pstat, param);rst = pstat.executeQuery();LIS.Core.Util.LogUtils.WriteSqlLog("参数:" + paraSql);//标识是否第一行boolean isFirstRow = true;while (rst.next()) {rowCount++; //总行数加一//查询全部,或者取分页范围内的记录if (findAll || (rowCount > fromRow && rowCount <= toRow)) {ResultSetMetaData metaData = rst.getMetaData();//获取列数int colCount = metaData.getColumnCount();//单行数据容器StringBuilder rowsb = new StringBuilder();rowsb.append("{");//标识是否第一列boolean isFirstCol = true;for (int coli = 1; coli <= colCount; coli++) {//获取列名String colName = metaData.getColumnName(coli);//获取列值Object colValue = rst.getObject(coli);if (colValue == null) colValue = "";//如果传了显示的字段,过滤不包含的字段if (fields != null && !fields.isEmpty() && fields.indexOf("," + colName + ",") < 0) {continue;}if (isFirstCol) {rowsb.append("\"" + colName + "\":");rowsb.append("\"" + JsonHelper.DealForJsonString(colValue.toString()).toString() + "\"");isFirstCol = false;} else {rowsb.append(",");rowsb.append("\"" + colName + "\":");rowsb.append("\"" + JsonHelper.DealForJsonString(colValue.toString()).toString() + "\"");}}rowsb.append("}");if (isFirstRow) {rowAllsb.append(rowsb.toString());isFirstRow = false;} else {rowAllsb.append(",");rowAllsb.append(rowsb.toString());}}}} catch (Exception ex) {//查询异常清空数据记录容器rowAllsb.delete(0, rowAllsb.length());}//操作结束释放资源,但是不断连接,不然没法连续做其他数据库操作了finally {if (rst != null) {rst.close();}if (pstat != null) {pstat.close();}//如果上层调用未开启事务,则调用结束释放数据库连接if (!Manager().Hastransaction) {manager.Close();}}//组装数据记录jsonsb.append(rowAllsb.toString());//补充数组结尾符jsonsb.append("]");if (returnCount) {jsonsb.append(",");jsonsb.append("\"total\":");jsonsb.append(rowCount);jsonsb.append("}");}return jsonsb.toString();}
然后反射得到实体jar包的所有实体类供码表管理器展示表
package LIS.DAL.ORM.DBUtility;import LIS.DAL.ORM.Common.ModelInfo;
import LIS.DAL.ORM.Common.ModelToSqlUtil;
import LIS.DAL.ORM.Common.TableInfo;
import java.io.File;
import java.io.FileInputStream;
import java.util.ArrayList;
import java.util.List;
import java.util.jar.JarEntry;
import java.util.jar.JarInputStream;/*** 给码表取实体信息工具类*/
public class ModelInfoUtil {/*** 得到所有的实体信息* @return*/public static String GetAllModelJson() throws Exception{List<ModelInfo> retList=new ArrayList<>();//得到实体的所有类List<Class> list=LIS.Core.Util.ReflectUtil.GetAllType("LIS.Model","LIS.Model.Entity");if(list!=null&&list.size()>0){for(int i=0;i<list.size();i++){Class c=list.get(i);Object m=c.getConstructor().newInstance();ModelInfo model=new ModelInfo();TableInfo tableInfo=ModelToSqlUtil.GetTypeInfo(m);model.Name=c.getSimpleName();if(tableInfo.TableInfo!=null){model.Remark=tableInfo.TableInfo.Remark();model.TableName=tableInfo.TableInfo.Name();model.PropNames=new ArrayList<>();for(int j=0;j<tableInfo.ColList.size();j++){model.PropNames.add(tableInfo.ColList.get(j).Name);}}retList.add(model);}}return LIS.Core.Util.JsonUtil.Object2Json(retList);}}
反射得到所有实体
package LIS.Core.Util;import java.io.File;
import java.lang.reflect.Field;
import java.lang.reflect.Type;
import java.net.URL;
import java.net.URLClassLoader;
import java.util.ArrayList;
import java.util.Enumeration;
import java.util.List;
import java.util.jar.JarEntry;
import java.util.jar.JarFile;/*** 反射工具类*/
public class ReflectUtil {/*** 设置对象指定属性名字的值* @param obj 对象* @param name 属性名称* @param val 属性值*/public static void SetObjValue(Object obj,String name,Object val){try {Class c = obj.getClass();//得到列信息Field declaredField = c.getDeclaredField(name);//布尔的处理if(declaredField.getType()==Boolean.class) {if(val.toString().equals("1")){val=Boolean.TRUE;}else if(val.toString().equals("0")){val=Boolean.FALSE;}else{val=null;}}//布尔的处理else if(declaredField.getType()==boolean.class) {if(val.toString().equals("1")){val=true;}else if(val.toString().equals("0")){val=false;}else{val=true;}}//int的处理else if(declaredField.getType()==int.class) {if(val==null){val=0;}}//数字的处理else if(declaredField.getType()==Integer.class||declaredField.getType()==Double.class||declaredField.getType()==Float.class) {if(val.toString().isEmpty()){val=null;}}declaredField.set(obj, val);}catch (Exception ex){ex.printStackTrace();}}/*** 用类型全名和程序集全名获得类型* @param typeName 类型全面* @param assemblyName 程序集名* @return 类型*/public static Class GetType(String typeName, String assemblyName){try {//得到根路径Class<?> clazz = ReflectUtil.class;ClassLoader classLoader = clazz.getClassLoader();URL resourceURL1 = classLoader.getResource("");String bashePath = resourceURL1.getFile();//组装成jar包路径String jarPath=bashePath+assemblyName+".jar";File file = new File(jarPath);if (!file.exists()) {throw new Exception("未能找到"+jarPath+"的文件");}//反射得到类型//自己生成jar包路径URL url = file.toURI().toURL();URL[] urls = new URL[]{url};//加载程序集URLClassLoader loader = new URLClassLoader(urls, ReflectUtil.class.getClassLoader());//加载类Class c = loader.loadClass(typeName);if(c!=null){return c;}else{throw new Exception("未能构建类型"+typeName);}}catch (Exception ex){ex.printStackTrace();}return null;}/*** 得到jar包下所有类* @param assemblyName jar包名称* @param packageName 包名* @return*/public static List<Class> GetAllType(String assemblyName,String packageName) throws Exception{List<Class> classes = new ArrayList<>();try {//得到根路径Class<?> clazz = ReflectUtil.class;ClassLoader classLoader = clazz.getClassLoader();URL resourceURL1 = classLoader.getResource("");String bashePath = resourceURL1.getFile();//组装成jar包路径String jarPath=bashePath+assemblyName+".jar";File file = new File(jarPath);if (!file.exists()) {throw new Exception("未能找到"+jarPath+"的文件");}//反射得到类型//自己生成jar包路径URL url = file.toURI().toURL();URL[] urls = new URL[]{url};//加载程序集URLClassLoader loader = new URLClassLoader(urls, ReflectUtil.class.getClassLoader());try (JarFile jarFile = new JarFile(jarPath)) {Enumeration<JarEntry> entries = jarFile.entries();while (entries.hasMoreElements()) {JarEntry entry = entries.nextElement();if (entry.getName().endsWith(".class")) {String className = entry.getName().replace(".class", "").replace("/", ".");Class c = loader.loadClass(className);classes.add(c);}}}}catch (Exception ex){ex.printStackTrace();}return classes;}
}
码表后台实现,按传入的实体名称反射查询带外键的数据供界面展示
解析表的信息供前端渲染界面
package LIS.DAL.ORM.Common;
import LIS.Core.CustomAttributes.FrekeyAttribute;
import LIS.Core.CustomAttributes.IdAttribute;
import LIS.Core.CustomAttributes.NotNullAttribute;
import LIS.Core.CustomAttributes.UniqueAttribute;
import jdk.jshell.execution.Util;import java.lang.annotation.Annotation;
import java.lang.reflect.Field;
import java.util.ArrayList;
import java.util.Hashtable;
import java.util.List;/*** 通用码表的界面配置实体*/
public class ModelConfig{/*** 实体名称*/public String ModelName;/*** 实体显示名称*/public String ShowModelName;/*** 是否分页*/public Boolean Pagination;/*** 页面显示行数*/public int PageSize;/*** 是否适应屏幕显示*/public Boolean fitColumns;/*** 是否显示行号*/public Boolean rowNumber;/*** 实体属性*/public List<ModelProperty> ModelPropertys;/*** 编辑窗口的宽度*/public int Width;/*** 编辑窗口的高度*/public int Height;/*** 编辑窗口的标签宽度*/public int LabelWidth;/*** 最大行*/public int MaxRowLen = 8;/*** 唯一列要求*/public List<String> UniqueColumns;/*** 默认排序串* @return*/public String SortNames(){String ret = "";for(int i=0;i<ModelPropertys.size();i++){ModelProperty pro=ModelPropertys.get(i);if (pro.PropertyName == "Sequence" && ModelName != "BTHRStaff"){ret = "Sequence";}else if (pro.PropertyName == "SeqNum" && ModelName != "BTHRStaff"){ret = "SeqNum";}}if (ret == ""){ret = "RowID";}return ret;}/*** 停靠*/public enum DisplayPosition{CENTER, LEFT, RIGHT}/*** 输入框类型*/public enum InputType{TEXT, SELECT, FR_SELECT, DETAIL_TABLE}/*** 列的数据类型*/public enum ColumnType{INT, STRING, BOOL, FLOAT, DOUBLE, OTHER};/*** 属性类*/public class ModelProperty{/*** 属性名称*/public String PropertyName;/*** 属性显示名称*/public String ShowPropertyName;/*** 是否显示*/public Boolean IsShow;/*** 显示宽度*/public int ShowWidth;/*** 是否是表的详细列*/public boolean IsDtTable = false;/*** 是否禁止选择*/public boolean IsDisable = false;/*** 禁止选择的制定值*/public String DisableVal;/*** 停靠CENTER, LEFT, RIGHT*/public DisplayPosition DisplayPosition;/*** 显示位置*/public DisplayPosition ShowPosition;/*** 输入框类型TEXT, SELECT, FR_SELECT, DETAIL_TABLE*/public InputType InputType;/*** 编辑类型*/public InputType EditType;/*** 编辑样式*/public String EditStyle;/*** 数据类型*/public ColumnType DataType;/*** 最大长度*/public int MaxLength;/*** 限选数据,用于枚举*/public Hashtable Selects;/*** 限选数据串*/public String SelectsStr;/*** 序号*/public int Sequence;/*** 是否为主键*/public boolean IsId;/*** 是否为主键*/public boolean IsFK;/*** 是否是系统强制要求必填*/public boolean IsMustRequire;/*** 是否必填*/public boolean IsRequire;/*** 是否关联外键*/public ModelPropertyFK PropertyFK;/*** 外键内部类*/public class ModelPropertyFK{/*** 外键实体名称*/public String FkModelName;/*** 外键关联字段*/public String FefColumnName;/*** 外键拉取知道*/public String AssociaField;/*** 外键选择数据,8.4废弃*/public Hashtable FkSelects; //外键相关的所有数据/*** 构造*/public ModelPropertyFK(){}/*** 构造* @param FkModelName 参照的表实体* @param FefColumnName 参照列* @param AssociaField 拉取列*/public ModelPropertyFK(String FkModelName, String FefColumnName, String AssociaField){this.FkModelName = FkModelName;this.FefColumnName = FefColumnName;this.AssociaField = AssociaField;}}/*** 构造*/public ModelProperty(){}/*** 构造* @param pi*/public ModelProperty(Field pi){this.PropertyName = pi.getName();this.ShowPropertyName = pi.getName();this.IsShow = true;this.ShowWidth = 100;this.ShowPosition = DisplayPosition.CENTER;this.EditType = InputType.TEXT;this.EditStyle = "";this.MaxLength = 80;if (pi.getType() == int.class || pi.getType() == Integer.class){this.DataType = ColumnType.INT;}else if (pi.getType() == float.class || pi.getType() == Float.class){this.DataType = ColumnType.FLOAT;}else if (pi.getType() == double.class || pi.getType() == Double.class){this.DataType = ColumnType.DOUBLE;}else if (pi.getType() == boolean.class || pi.getType() == Boolean.class){this.DataType = ColumnType.BOOL;}else if (pi.getType() == String.class){this.DataType = ColumnType.STRING;}else{this.DataType = ColumnType.OTHER;}if (pi.getName().endsWith("Date") || pi.getName().endsWith("Time")){//给定默认的宽度this.EditStyle = "width:146px;";}this.Selects = new Hashtable();this.SelectsStr = LIS.Core.Util.JsonUtil.Object2Json(this.Selects);if (pi.getType() == boolean.class || pi.getType() == Boolean.class){this.EditType = InputType.SELECT;this.EditStyle = "width:146px;";this.DataType = ColumnType.BOOL;this.Selects.put("1", "true");this.Selects.put("0", "false");this.SelectsStr = "{\"1\":\"true\",\"0\":\"false\"}";}//返回所有自定义特性Annotation[] propertyAttrs = pi.getAnnotations();//遍历所有自定义特性for (int i = 0; i < propertyAttrs.length; i++){//获取当前的自定义特性Annotation propertyAttr = propertyAttrs[i];//如果是主键特性if (propertyAttr instanceof IdAttribute){this.IsId = true;}//如果是外键特性else if (propertyAttr instanceof FrekeyAttribute){this.IsFK = true;FrekeyAttribute fkAttr = (FrekeyAttribute)propertyAttr;this.PropertyFK = new ModelPropertyFK(fkAttr.Name(), fkAttr.RefColumnName(), fkAttr.AssociaField());//给定默认的宽度this.EditStyle = "width:146px;";}//是否必填else if (propertyAttr instanceof NotNullAttribute){this.IsRequire = true;this.IsMustRequire = true;}}}//将字符串形式的选择数据转换为Map(hashtable)public void SetSelects(){this.Selects = (Hashtable) LIS.Core.Util.JsonUtil.Json2Object(this.SelectsStr,Hashtable.class);}}/*** 空构造函数*/public ModelConfig(){}/*** 根据类型初始化配置文件* @param type*/public ModelConfig(Class type){this.ModelName = type.getSimpleName();this.ShowModelName = type.getSimpleName();this.Pagination = true;this.PageSize = 20;this.rowNumber = false;this.Width = 600;this.Height = 400;this.LabelWidth = 240;this.UniqueColumns = new ArrayList<>();this.ModelPropertys = new ArrayList<>();Field[] propertyInfos = type.getFields();if (propertyInfos.length > 10){this.fitColumns = false;}else{this.fitColumns = true;}if (propertyInfos.length == 0){return;}ModelProperty mp = null;for(int i=0;i<propertyInfos.length;i++){Field pi=propertyInfos[i];mp = new ModelProperty(pi);this.ModelPropertys.add(mp);}//读取唯一组合键Annotation[] attrs = type.getAnnotations();for(int i=0;i<attrs.length;i++){Annotation attr=attrs[i];if(attr instanceof UniqueAttribute){//as转换类型UniqueAttribute attr_ = (UniqueAttribute)attr;if (attr_.ColNames().toLowerCase().equals("RowID".toLowerCase())){continue;}//得到w唯一组合键this.UniqueColumns.add(attr_.ColNames().replace(',', '+'));}}}}
基于此,只要实力足够强劲,即可实现通用码表,我带来的独创设计。框架实现到检验目前同水准或者超越的时候,借助脚本化、码表、代码生成、打印导出、模板设计器、虚拟M脚本这些实现、足以搅局整个需求型软件行业,我熟悉的是医疗;效率和发布型的架构相比就是高很多。
框架计划
相关文章:

jbase实现通用码表
没有通用码表的体系是不完美的,当年我用C#能实现的通用码表,现在在java一样的实现了,通用码表对提高开发效率和降低开发成本的作用巨大,开发可以专注写业务,而不必被太多的维护界面束缚。进而体现在产品竞争力上面&…...

工业镜头中的远心镜头与普通镜头的光路
普通镜头: 主光线与镜头光轴有角度,工件上下移动时,像的大小有变化。 FOV>镜头前端直径。 物方远心镜头: 物方主光线平行于光轴,物距发生改变时,像高不会发生改变,测得的物体尺寸大…...

【Qt之QWizardPage】使用
介绍 QWizardPage类是向导页面的基类。 QWizard表示一个向导。每个页面都是一个QWizardPage。当创建自己的向导时,可以直接使用QWizardPage,也可以子类化它以获得更多控制。 页面具有以下属性,由QWizard呈现:a title,…...

自动化测试,5个技巧轻松搞定
想要在质量保证团队中赢得核心?当你组建你的网络应用时要记住这些技巧,可以变得更容易分析并快速创建更多准确可重复的自动化测试。 1.歧义是敌人 尽可能使你的代码具体化。当然,你已经遵循了W3C标准,对吗?以下有三件…...
EasyWeChat调用企业微信接口获取客户群数据
use EasyWeChat\Factory; use fast\Http;$config [corp_id > Config::get(site.corp_id),agent_id > Config::get(site.agend_id), // 如果有 agend_id 则填写secret > Config::get(site.agent_secret),// 指定 API 调用返回结果的类型:array(default)…...

sql 左联 右联
...
k8s中的端口hostPort、port、nodePort、targetPort
hostPort:apiVersion: v1 kind: Pod metadata:name: tomcat spec:containers:- name: tomcatimage: tomcat:8.5ports:- hostPort: 8081containerPort: 8080protocol: TCPhostPort 类似docker -p 参数做的端口映射,将容器内端口映射到宿主机上(hostPort), 在k8s中&am…...

自动发微博脚本工具,可批量定时发送,按键精灵完全开源版
就跟标题上面讲的,软件是我之前开发好的,所有功能都能用,是按键精灵的脚本,只是单设备操作,也可以在模拟器下面操作,UI代码方面都设计的很完整,我这边就干脆分享出来给大家用,不用繁…...

2023版Idea创建JavaWeb时,右键new没有Servlet快捷键选项
问题:右键时,没有创建servlet的快捷键,如下图: 解决方法: 1.打开idea,点击File>settings(设置),进入settings页面,如下 从上图中的Files选项中没看到有servlet选项,…...

数据结构(c语言版本) 二叉树的遍历
要求 实现二叉树的创建,并输入二叉树数据 然后先序遍历输出二叉树、中序遍历输出二叉树、后序输出二叉树 输出二叉树的深度、二叉树的叶子结点 例如二叉树为: 该二叉树的先序遍历结果为: A B D C E F 该二叉树的中序遍历结果为:…...

Django 配置 Email Admin 详细指南
概要 Django 是一个高级的 Python Web 框架,它鼓励快速开发和清洁、实用的设计。当你正在开发一个 Django 项目时,监控网站的运行情况是非常必要的。Django 提供了一个功能强大的 admin 界面,但同时也可以通过配置 email admin 来获取网站的…...

Apache阿帕奇安装配置
目录 一、下载程序 1. 点击Download 2. 点击Files for Microsoft Windows 3. 点击Apache Lounge 4. 点击httpd-2.4.54-win64-VSI6.zip 5. 下载压缩包 6.解压到文件夹里 二、配置环境变量 1. 右键我的电脑 - 属性 2. 高级系统设置 3. 点击环境变量 4. 点击系统变…...

时间序列预测实战(十六)PyTorch实现GRU-FCN模型长期预测并可视化结果
往期回顾:时间序列预测专栏——包含上百种时间序列模型带你从入门到精通时间序列预测 一、本文介绍 本文讲解的实战内容是GRU-FCN(门控循环单元-全卷积网络),这是一种结合了GRU(用于处理时间序列数据)和FCN(全卷积网络…...

如何提升软件测试效率?本文为你揭示秘密
在软件开发中,测试是至关重要的一个环节。它能帮助我们发现并修复问题,从而确保我们提供的软件具有高质量。然而,测试过程往往费时费力。那么,有没有方法可以提升我们的软件测试效率呢?答案是肯定的。下面,…...
参数估计和非参数估计
一、参数估计 参数估计是统计学中的一个重要概念,它涉及到使用样本数据来估计总体参数的过程。在统计学中,总体是指研究对象的整体集合,而样本是从总体中抽取的部分元素。 参数估计有两种主要方法:点估计和区间估计。 点估计&am…...

Apache Airflow (八) :DAG任务依赖设置
🏡 个人主页:IT贫道_大数据OLAP体系技术栈,Apache Doris,Clickhouse 技术-CSDN博客 🚩 私聊博主:加入大数据技术讨论群聊,获取更多大数据资料。 🔔 博主个人B栈地址:豹哥教你大数据的个人空间-豹…...
使用 com.jacob.activeX 库实现 Word 到 PDF
使用 com.jacob.activeX 库实现 Word 到 PDF 的转换涉及到使用 Java 和 Microsoft Office 的 COM 自动化。JACOB(Java COM Bridge)库提供了一个桥接器,允许 Java 代码通过 COM(组件对象模型)与 Windows 应用程序&#…...

2023亚太杯数学建模思路 - 案例:FPTree-频繁模式树算法
文章目录 算法介绍FP树表示法构建FP树实现代码 建模资料 ## 赛题思路 (赛题出来以后第一时间在CSDN分享) https://blog.csdn.net/dc_sinor?typeblog 算法介绍 FP-Tree算法全称是FrequentPattern Tree算法,就是频繁模式树算法,…...

Dart利用私有构造函数_()创建单例模式
文章目录 类的构造函数_()函数dart中构造函数定义 类的构造函数 类的构造函数有两种: 1)默认构造函数: 当实例化对象的时候,会自动调用的函数,构造函数的名称和类的名称相同,在一个类中默认构造函数只能由…...
简述如何使用Androidstudio对文件进行保存和获取文件中的数据
在 Android Studio 中,可以使用以下方法对文件进行保存和获取文件中的数据: 保存文件: 创建一个 File 对象,指定要保存的文件路径和文件名。使用 FileOutputStream 类创建一个文件输出流对象。将需要保存的数据写入文件输出流中…...
生成xcframework
打包 XCFramework 的方法 XCFramework 是苹果推出的一种多平台二进制分发格式,可以包含多个架构和平台的代码。打包 XCFramework 通常用于分发库或框架。 使用 Xcode 命令行工具打包 通过 xcodebuild 命令可以打包 XCFramework。确保项目已经配置好需要支持的平台…...

手游刚开服就被攻击怎么办?如何防御DDoS?
开服初期是手游最脆弱的阶段,极易成为DDoS攻击的目标。一旦遭遇攻击,可能导致服务器瘫痪、玩家流失,甚至造成巨大经济损失。本文为开发者提供一套简洁有效的应急与防御方案,帮助快速应对并构建长期防护体系。 一、遭遇攻击的紧急应…...
Java 语言特性(面试系列1)
一、面向对象编程 1. 封装(Encapsulation) 定义:将数据(属性)和操作数据的方法绑定在一起,通过访问控制符(private、protected、public)隐藏内部实现细节。示例: public …...
在鸿蒙HarmonyOS 5中实现抖音风格的点赞功能
下面我将详细介绍如何使用HarmonyOS SDK在HarmonyOS 5中实现类似抖音的点赞功能,包括动画效果、数据同步和交互优化。 1. 基础点赞功能实现 1.1 创建数据模型 // VideoModel.ets export class VideoModel {id: string "";title: string ""…...

12.找到字符串中所有字母异位词
🧠 题目解析 题目描述: 给定两个字符串 s 和 p,找出 s 中所有 p 的字母异位词的起始索引。 返回的答案以数组形式表示。 字母异位词定义: 若两个字符串包含的字符种类和出现次数完全相同,顺序无所谓,则互为…...

k8s业务程序联调工具-KtConnect
概述 原理 工具作用是建立了一个从本地到集群的单向VPN,根据VPN原理,打通两个内网必然需要借助一个公共中继节点,ktconnect工具巧妙的利用k8s原生的portforward能力,简化了建立连接的过程,apiserver间接起到了中继节…...

力扣热题100 k个一组反转链表题解
题目: 代码: func reverseKGroup(head *ListNode, k int) *ListNode {cur : headfor i : 0; i < k; i {if cur nil {return head}cur cur.Next}newHead : reverse(head, cur)head.Next reverseKGroup(cur, k)return newHead }func reverse(start, end *ListNode) *ListN…...
scikit-learn机器学习
# 同时添加如下代码, 这样每次环境(kernel)启动的时候只要运行下方代码即可: # Also add the following code, # so that every time the environment (kernel) starts, # just run the following code: import sys sys.path.append(/home/aistudio/external-libraries)机…...

从 GreenPlum 到镜舟数据库:杭银消费金融湖仓一体转型实践
作者:吴岐诗,杭银消费金融大数据应用开发工程师 本文整理自杭银消费金融大数据应用开发工程师在StarRocks Summit Asia 2024的分享 引言:融合数据湖与数仓的创新之路 在数字金融时代,数据已成为金融机构的核心竞争力。杭银消费金…...

【Linux手册】探秘系统世界:从用户交互到硬件底层的全链路工作之旅
目录 前言 操作系统与驱动程序 是什么,为什么 怎么做 system call 用户操作接口 总结 前言 日常生活中,我们在使用电子设备时,我们所输入执行的每一条指令最终大多都会作用到硬件上,比如下载一款软件最终会下载到硬盘上&am…...