android 手把手教你写数据库框架(第一篇)

Android Studio-手把手教你基于SQLLITE实现登录注册功能 继启动界面之后,现在开始做登录界面和注册界面。需要看启动界面教学的,请戳我的博客: Android Studio之启动界面教学 Android Studio之启动界面教学. 其实安卓的登录注册,和JAVA是一样的,甚至于是极简版的JAVA登录注册,安卓太智能了,数据保存在sqllite中,完全不需要导包,而且还伴有可视化界面,简直无敌,安卓可以说是目前我们学过的最简单的语言,只是大家没有好好学罢了... 阅读详情

前言:当你想成为什么样的人,努力朝目标努力,终究有一天会实现,人生最大的快乐就是不断追寻梦想的过程


准备写一个数据库框架,现在的项目中数据库框架是用三方orm,不知道是不是叫这个名字,不重要了,准备这段时间把这数据库框架写出来,也许写的不够好,没关系,只要坚持住总会比之前好,这就是进步,我们如果不使用数据库框架的话,写的步骤可能要多点,现在就开始准备写,把这个框架命名为android_simple_sqlite


我们之前创建的数据库文件都是放在data/data/packageName/xxx.db,放在这里有一个不好的地方在于如果这个apk被用户卸载了,那么这个数据库也会跟着没了,如果项目需求要求你是在apk被卸载了后,apk第二次被安装时要求做什么功能需要用到之前数据库,那么这个时候你把数据库放在data/data/packageName/xxx.db就歇菜了!所以我们要针对这部分可以让数据库文件根据用户的需求存放在哪?


现在画一个架构设计图:


看下我的项目包结构:


uml类图如下:




上面的图可能画的不够好,就就将着看下吧,我们在上层只是和DaoFactory这个类打交道,调用getDataHelper()方法返回BaseDao,看下调用层基本调用:

baseDao = DaoFactory.getInstance(this).getDataHelper(UserDao.class,User.class);
User user = new User();
user.setAge(18);
user.setName("zhouguizhi");
user.setPassword("123456");
baseDao.insert(user);
发现在调用层只要传递对应的实体和操作实体的BaseDao子类即可,因为底层不知道你操作的是什么具体数据,所以要用到泛型,哪为什么要getDataHelper()方法中要用到二个泛型呢?

第一个泛型是对数据库进行增删改查的具体业务类,你不可能操作User实体对象你传递一个PersonDao,这样会导致去获取实体对象中的属性以及属性上的注解会出现问题

第二个泛型是对那个实体对象进行操作

public  synchronized  <T extends BaseDao<M>,M> T getDataHelper(Class<T> clazz, Class<M> entityClass)
{
    BaseDao baseDao=null;
    try {
        baseDao=clazz.newInstance();
        baseDao.init(entityClass,sqLiteDatabase);
    } catch (InstantiationException e) {
        e.printStackTrace();
    } catch (IllegalAccessException e) {
        e.printStackTrace();
    }
    return (T) baseDao;
}
这是在DataFactory类中获取到BaseDao,具体操作肯定是BaseDao的子类了,既然是框架所以我们想自动的创建表,而不需要手动的去创建,所以我们要使用注解把字段和表结构对应起来,
package com.sqlite.annotation;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
/**
 * Created by admin on 2017/2/6.
 */
@Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)
public @interface AnnTableName {
    String value();
}
这是每个bean实体上的注解,用于声明表名:
package com.sqlite.annotation;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
@Target(ElementType.FIELD)
@Retention(RetentionPolicy.RUNTIME)
public @interface AnnFiled {
    String columnName() default "";//字段名
    String  type() default "";//字段类型
    int len() default 0;//字段长度
}
上面的注解用于实体bean上属性上,你会发现我AnnFiled注解上定义了三个属性

columnName:表示表名

type:表示字段什么类型的

len:默认的字段多少长度

使用:

package com.sqlite.bean;
/**
 * Created by admin on 2017/2/6.
 */
import com.sqlite.annotation.AnnFiled;
import com.sqlite.annotation.AnnTableName;
@AnnTableName("user")
public class User {
    @AnnFiled(columnName = "age",type ="Integer")
    public int age;
    @AnnFiled(columnName = "name",type ="varchar",len = 20)
    public String name;
    @AnnFiled(columnName = "pwd",type ="varchar",len = 20)
    public String password;
    public int getAge() {
        return age;
    }
    public void setAge(int age) {
        this.age = age;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public String getPassword() {
        return password;
    }
    public void setPassword(String password) {
        this.password = password;
    }
}
到时候我们只要通过反射去获取类和属性上的注解就可以动态的创建表语句

但是前提我们要让表名和实体bean属性对应起来,而且还有可能就bean上的属性名和表名不一致的情况,所以我们第一步就要把这关系对应上,第二次就不用了,这就是为什么要在BaseDao中init()方法的作用:


BaseDao.java

/**
 * 初始化 主要是映射关系是否建立 以及
 * @param entityClass
 * @param sqLiteDatabase
 * @param
 */
public synchronized boolean init(Class<T> entityClass, SQLiteDatabase sqLiteDatabase) {
    if(!isInit){
        this.dataBase = sqLiteDatabase;
        this.clazz = entityClass;
        if(dataBase!=null){
            if(!dataBase.isOpen()){//判断数据库是否打开
                return false;
            }
        }
        String sql = "";
        if(clazz.getAnnotation(AnnTableName.class)!=null){
            tbName = clazz.getAnnotation(AnnTableName.class).value();
        }else{
            tbName = clazz.getSimpleName().toLowerCase();
        }
        try {
            sql =  createTable(clazz.newInstance());
        } catch (InstantiationException e) {
            e.printStackTrace();
        } catch (IllegalAccessException e) {
            e.printStackTrace();
        }
        if(!TextUtils.isEmpty(sql)){
            dataBase.execSQL(sql);//创建表
        }
        cacheMap = new HashMap<>();
        initCacheMap();
        isInit = true;
    }
    return isInit;
}
这是init()方法,如果数据库没有打开,就什么操作都不做了,如果数据库打开了就获取表名和上面说的对应关系,那么数据库我们在哪打开呢?

我们在DataFactory类做成了单例,在构造函数中做数据库创建和打开的操作

private DaoFactory(){
    dbFilePath= FileUtils.getDataBasePath(ctx,"zgz","user.db");
    LogUtils.e("dbFilePath="+dbFilePath);
    openDatabase();
}
上面dbFilePath是你数据库存放的路径在哪,我们平时数据库都是通过几次SqliteOpenHelper,那么这时候默认在data/data/package/database/xx.db,在这个框架中默认是在sd卡中如果sd卡不存在就放在其他目录下.

打开或者创建数据库的方法如下:

/**
 * 打开数据库
 */
private void openDatabase() {
    this.sqLiteDatabase=SQLiteDatabase.openOrCreateDatabase(dbFilePath,null);
}
在上面的BaseDao类上的init()方法中我们是先要创建一个表,为什么?因为等下我要拿到表中的所有字段名,不创建表怎么能拿的到,
try {
    sql =  createTable(clazz.newInstance());
} catch (InstantiationException e) {
    e.printStackTrace();
} catch (IllegalAccessException e) {
    e.printStackTrace();
}
if(!TextUtils.isEmpty(sql)){
    dataBase.execSQL(sql);//创建表
}
上面的createTable()方法是BaseDao中的一个抽象方法,UserDao是继承了BaseDao,所以要实现这个createTable()方法,这个方法就是自动创建表的过程
package com.sqlite.dao;
import com.sqlite.annotation.AnnFiled;
import com.sqlite.annotation.AnnTableName;
import com.sqlite.bean.User;
import com.sqlite.constant.Constant;
import com.sqlite.dao.base.BaseDao;
import com.sqlite.utils.LogUtils;
import java.lang.reflect.Field;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
/**
 * Created by admin on 2017/2/6.
 */
public class UserDao extends BaseDao<User> {
    @Override
    protected String createTable(User user) {
        String tb_name =  User.class.getAnnotation(AnnTableName.class).value();
        Field[] fields =  User.class.getDeclaredFields();
        String fieldName = "";
        String type = "";
        int len = 0;
        Map<String,Field> columsMap = new HashMap<>();
        for(Field field:fields){
            columsMap.put(field.getName(),field);
        }
        StringBuffer sb = new StringBuffer(Constant.create_table_prix);
        sb.append(" ");
        sb.append(tb_name);
        boolean isFirst = false;
        int i=0;
        for (Map.Entry<String, Field> entry: columsMap.entrySet()) {
            Field filed = entry.getValue();
            if(!isFirst){
                isFirst = true;
                sb.append("(");
            }
            if(filed.getAnnotation(AnnFiled.class)!=null){
                fieldName=filed.getAnnotation(AnnFiled.class).columnName();
                type = filed.getAnnotation(AnnFiled.class).type();
                len = filed.getAnnotation(AnnFiled.class).len();
                sb.append(fieldName).append(" ").append(type).append(len>0?"("+len+")":"").append((i==columsMap.size()-1)? ")":",");
                i++;
            }
        }
        LogUtils.e(sb.toString());
        return sb.toString();
    }

    @Override
    public Long insert(List<User> entity) {
        return null;
    }
}
这是通过反射和注解对创建表语句的拼写!

表创建成功了后就是找映射关系了,封装在initCacheMap()方法中,画一个图就理解了


用文字太难描述了,可能是文采太差的原因,还是画图好

FileUtils.java是对文件操作的工具类在这贴下:

package com.sqlite.utils;
import android.content.Context;
import android.os.Environment;
import android.text.TextUtils;
import java.io.File;
import java.io.IOException;
/**
 * Created by Adminis on 2017/2/6.
 */
public class FileUtils {
    /**
     * 判断sd卡是否存在
     * @return
     */
    public static boolean sdCardIsExites(){
        if(Environment.getExternalStorageState().equals(android.os.Environment.MEDIA_MOUNTED)){
                return true;
        }
        return false;
    }
    /**
     * 获取sd卡根目录
     * @return
     */
    public static String getPath(){
        String path = "";
        if(sdCardIsExites()){
            path = Environment.getExternalStorageDirectory().getAbsolutePath();
        }
        return path;
    }
    /**
     * 在sd卡下面创建一个目录
     */
    public static String createFolder(Context context, String folderName){
        File file = null;
        String sdRootPath = getPath();
        if(TextUtils.isEmpty(sdRootPath)){//表示sd卡不存在
            if(context!=null){
                // /data/data/com.sqlite/files/zhgougui
                file = new File(context.getFilesDir().getAbsolutePath()+File.separator+folderName);
            }
        }else{
            file = new File(sdRootPath+File.separator+folderName);
        }
        if(file!=null&&!file.exists()){
            file.mkdir();
        }
        return file.getAbsolutePath();
    }

    /**
     *
     * @param ctx 上下文
     * @param folderName 文件夹名
     * @param dataBaseName 数据库名
     * @return
     */
    public static String getDataBasePath(Context ctx,String folderName,String dataBaseName){
        String dbPath = "";
        String dirPath = createFolder(ctx,folderName);
        File file = new File(dirPath+File.separator+dataBaseName);
        if(file!=null&&!file.exists()){
            try {
                file.createNewFile();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        dbPath = file.getAbsolutePath();
        return dbPath;
    }
}
现在插入一条数据试试看!
/**
 * 插入单条数据
 */
private void addSingleData() {
    User user = new User();
    user.setAge(18);
    user.setName("zhouguizhi");
    user.setPassword("123456");
    baseDao.insert(user);
}
运行起来发现在我们sd卡目录下创建的zgz目录存放了数据库文件user.db



看下user表什么都没:


我们现在点击下button


现在再把数据库文件导入出来看看:


ok,数据是插入成功了,这是做单条数据插入,有时间会把插入多条数据逻辑写下,我把我项目放在这博客中,有需要看的去下载看下,用文字描述太难,不知道怎么说!

代码下载地址:

http://download.youkuaiyun.com/detail/coderinchina/9748953






安卓微信本地数据库解密 安卓微信数据库解密 阅读详情

相关推荐

安卓Room框架初使用

安卓Room框架初使用Room框架介绍Database(数据库)Entity:表示数据库中的表。表的复杂写法:DAO:包含用于访问数据库的方法。具体使用(附Demo)添加依赖数据库的建立数据库的升级表结构的修改Entity代码Dao代码表的增删改查操作执行效果总结 Room框架介绍 Room在·SQLite上提供了抽象层,以便于更加流畅的访问数据库,对数据库进行操作。主要由Database,Entity,Dao这三部分组成: Database(数据库) 包含数据库持有者,并作为应用已保留的持久关系型数据的底

qq_42462966的博客 2208

android毕业设计——基于Android+XAMPP+MySQL的家校互动平台设计与实现(毕业论文+程序源码)——家校互动平台

学校教育与家庭教育的不一致,容易产生教育断层的局面,而现有的校讯通等家校互动平台,又存在教师与家长单向沟通等方面的问题。如今信息技术的飞速发展为家校共育的健康发展提供了强有力的保障,“互联网+”已成趋势。学校和教师要一改过去传统的沟通交流方式,借用互联网与手机短信相结合的家校互动信息平台,扩展沟通交流渠道,架起家校沟通的桥梁,从而让家校教育形成合力,提高教育的时效性,促进学生健康成长。因此,本文就目前“互联网+教育”的新趋势进行了说明,以明确进行研究的目的。

m0_66238867的博客 2275

Android数据库:SQLite除了.db文件,还多出.db-shm,.db-wal文件

Android数据库:SQLite除了.db文件,还多出.db-shm,.db-wal文件 使用安卓数据库保存文件时,在Android Studio 的 Device File Explorer里数据库文件目录 /data/data/com.urovo.datatopc/databases/DATA.db 发现其目录下不仅有.db文件,还有两个其他文件 .db-shm和.db-wal文件 而且数据库存储文件DATA.db(这是我的数据库名字,你们的可能不一样)保存至本地,通过SQLite Develope

m0_53581523的博客 4940

毕业设计:基于Android开发的健康饮食推荐系统+论文源码

本文详细阐述了一个健康饮食推荐管理系统的设计与实现过程。系统采用模块化设计,分为管理员和用户两大功能模块,包含健康食谱管理、饮食记录、健康数据分析等核心功能。数据库设计遵循E-R模型和逻辑结构设计原则,构建了用户表、食谱表、健康数据表等10个数据表,确保数据完整性和系统稳定性。系统实现部分展示了管理员后台和用户端的完整界面设计,包括用户管理、食谱管理、论坛管理等17个功能界面的具体实现方案。整个系统以用户需求为核心,注重操作便捷性和数据准确性,为健康饮食管理提供了全面的信息化解决方案。

鑫鑫源码工作室的博客 930

Android Studio 使用插件Database Navigation 连接 sqlite数据库

Database Navigation 是一款在 Android Studio 开发环境中非常实用的插件,它主要致力于帮助开发者更便捷、高效地管理和操作数据库,尤其是在 Android 项目涉及到数据库相关开发工作时,能够提升开发体验与效率。

梁辰兴的博客 2556

关于unity安卓平台对数据库文件的读取

这是针对关于安卓平台对项目数据库文件的访问 刚来公司实习不久,开始了一个小项目demo,本来是用csv文件读取一些数据,然而老板开始要求用数据库来读取,因此我就简单的直接读取本机的数据库,在PC上运行没有问题。老板开始要求在安卓上运行,此时问题就出现了,安卓上是无法通过ip去访问数据库。其实可以通过访问网站来获取数据库的数据,但是对于我这种刚毕业的新手来说是无法实现的,只能妥协通过访问数据库导出来...

日尧的博客 2352

如何画架构图?

先说答案。画架构图分四步走: 第一,搞清楚要画的架构图的类型; 第二,确认架构图中的关键要素(比如产品、技术、服务); 第三,梳理关键要素之间的关联:包含、支撑、同级并列等; 第四,输出关联关系清晰的架构图。 应用架构图 接下来,我们作进一步解读: 一、架构图的定义及作用 什么是架构图?维基百科、百度百科其实都没有关于它的直接定义。不过我们可以进行拆分理解: 架构图=架构+图 这样问题就转化成,什么是架构,以及什么是图? 关于架构,百度百科上是这样定义的: 架构,又名软件架构,是.

Edraw_Max的博客 1万+

Android项目实战 —— 手把手教你实现一款本地音乐播放器Dora Music

今天带大家实现一款基于Dora SDK的Android本地音乐播放器app,本项目也作为Dora SDK的实践项目或使用教程。使用到开源库有[https://github.com/dora4/dora] 、[https://github.com/dora4/dcache-android] 等。先声明一点,本项目主要作为框架的使用教程,界面风格不喜勿喷。我们要开发一款Android App,首先要搭建基础框架,比如使用MVP还是MVVM架构?使用什么网络库?使用什么ORM库?很显然,作为Dora SDK的使用

跟着哆啦学Android 2517

android中的数据库操作

android中的数据库操作       android中的应用开发很难避免不去使用数据库,这次就和大家聊聊android中的数据库操作。   一、android内的数据库的基础知识介绍          1.用了什么数据库             android中采用的数据库是SQLite这个轻量级的嵌入式开源数据库,它是用c语言构建的。相关简介可以从链接查看。

Winiex's Blog 18万+

安卓db数据库查看工具——快速管理与分析SQLite数据库

SQLite 是 Android 内置的轻量级关系型数据库管理系统,为 Android 应用提供了一种高效、便捷的数据持久化方案。与传统的关系型数据库不同,SQLite 将数据库存储在文件系统中的单一文件内,从而简化了数据库的部署和管理。SQLite 支持标准的 SQL 语言,允许在没有服务器进程的情况下进行数据库操作,这使得它非常适合于资源有限的移动设备环境。在 Android 应用开发中,SQLite 数据库常用于本地数据存储、用户个性化设置记录以及应用内缓存。

weixin_32869687的博客 1941

android数据库框架

封装好的androidsqlite数据库框架,使用非常方便,只需创建一个实体类即可完成数据库的增删改查操作!

SQLite数据库及在Android开发中的基本使用,2024年最新美团nlp面试

Python所有方向的技术点做的整理,形成各个领域的知识点汇总,它的用处就在于,你可以按照下面的知识点去找对应的学习资源,保证自己学得较为全面。

2401_84183070的博客 1026

安卓开发:写入数据库

public void showPwdDialog(final String pwd){ AlertDialog.Builder dialog=new AlertDialog.Builder(MainActivity.this); dialog.setTitle("密码"); dialog.setIcon(R.drawable.icon); dialog.setCancelable(false); View view=LayoutInflater.from(MainActivity.this).inflate(R.layout.inflater_checkdialog, null); final EditText pwd1 = (EditText) view.findViewById(R.id.checkdialog_pwd1); Button ok=(Button) view.findViewById(R.id.checkdialog_ok); Button cancel=(Button) view.findViewById(R.id.checkdialog_cancel); ok.setOnClickListener(new OnClickListener() { @Override public void onClick(View v) { String str=pwd1.getText().toString().trim(); if(str.equals(pwd)){ ad.dismiss(); }else{ Toast.makeText(MainActivity.this, "密码错误", 3000).show(); pwd1.setText(""); } } });

查看安卓sqlite数据库工具:Android-Debug-Database

简要介绍 安卓开发过程中,有时需要查看sqlite数据库,核对数据.本文介绍Android-Debug-Database,非常好用. github地址:https://github.com/amitshekhariitbhu/Android-Debug-Database 功能: 支持查看手机该app的数据库和shared preference. 支持修改数据库和shared preferenc...

蓝不蓝编程 1521

uniapp+uniCloud实现微信小程序一键登录

(用户唯一标识),用户登录成功后,开发者服务器可以将openid和session_key保存,生成一个自定义登录态的token令牌响应给微信小程序,通过token可以查询openid和session_key,小程序下次请求只要携带着token就可以证明已经登录。这个API就是获取用户信息,每次请求都会弹出授权窗口(这个可能会不弹,这个要看你的版本,根据版本来定,不懂的可以留下评论),用户同意后会返回。到这里就可以实现微信一键登录了,快去试试吧,有问题可以在评论区留言,我看见会尽我知道的为你解答。

lb2917的博客 2576

基于PID的定速巡航控制系统设计【MATLAB源码+Word文档】

本文详细介绍了定速巡航控制是一种车辆驾驶辅助系统,它能让驾驶者在高速或长途驾驶时,设定一个固定的车速,然后车辆会自动维持这个速度行驶,无需驾驶者持续踩油门。这大大减轻了驾驶者的疲劳,同时也提高了行驶的安全性。PID定速巡航控制系统是一种利用比例(Proportional)、积分(Integral)和微分(Derivative)控制算法来实现车辆定速巡航的先进系统。这种系统能够根据设定的速度,自动调整油门开度或制动力度,使车辆保持恒定的速度行驶。这种控制系统具有响应速度快、控制精度高、稳定性好等优点。

weixin_761237174的博客 1667

Android访问外部DB文件

注:本文代码参考了网上的例子,忘了什么地址了,所以无法提供说明,原作者看到勿怪,可以提醒我加上。   有时候自己导入DB文件进行操作,和访问本地数据库有点差异。 首先在res下建立一个文件夹raw,然后把DB文件导入进去 然后写一个方法获取SQLiteDatabase private static SQLiteDatabase database; public static final

氵白的专栏 1万+

英飞凌TC3xx实战:PWM中点触发ADC采集+DMA自动搬运完整配置流程(基于ILLD库)

本文详细介绍了在英飞凌TC3xx系列微控制器上使用ILLD库实现PWM中点触发ADC采集并通过DMA自动搬运数据的完整配置流程。该方案适用于电机控制、电源管理等需要高精度定时采集的场景,通过GTM生成PWM信号、ADC采集和DMA传输实现全硬件自动化流程,显著提升系统效率。

weixin_42536058的博客 530

安卓 mysql 框架_自己动手写Android数据库框架

自己动手写Android数据库框架相信不少开发者跟我一样,每次都很烦恼自己写数据库,而且那些数据库语句也经常记不住。当然网上也有很多很好的数据库框架,你可以直接拿来用,但是 很多时候我们的项目,特别是一个小型的Andrond应用原本用到的数据库结构比较简单,没必要去用那些有点臃肿的框架。当然,即使你用那些框架,当你遇到问题时,你是否也得去修改它?你要修改别人的框架必须的读懂他人的设计代码。所以不管...

weixin_39928102的博客 235

不用写代码!用AIStarter 5.0.0离线包部署InfiniteTalk的完整指南(Windows/Mac/Linux全平台)

本文详细介绍了如何使用AIStarter 5.0.0离线包在Windows、Mac和Linux平台上零代码部署InfiniteTalk数字人。从环境准备、离线资源获取与验证,到全平台部署实操指南,提供了完整的本地化安装流程和优化建议,帮助用户快速实现AI项目的一键部署。

weixin_30275415的博客 272

【脑电分析系列】第7篇:频域分析基石 — 功率谱密度(PSD)的计算与常见方法对比

本文探讨了脑电图(EEG)频域分析的核心方法——功率谱密度(PSD)。通过对比基于快速傅里叶变换的周期图法和更稳健的Welch's方法,指出后者通过分段、加窗和平均处理,能有效降低估计方差,更适合分析非稳态的脑电信号。文章详细解析了关键参数设置对频率分辨率和统计稳定性的影响,并提供了Python计算实现。PSD分析将复杂的脑电信号转换为直观的频域特征,为研究认知功能和神经疾病提供重要依据。

qq_32516809的博客 1800

Android Studio | 使用Database Inspector 查看数据库 .db 文件,太方便了!

在涉及到数据库开发时,通常需要查看 SQLite 数据库文件(.db),以调试数据存储是否正确。然而,由于Android 设备的 数据隔离机制,普通应用无法直接访问目录下的数据库文件。除了将数据库文件导出然后利用三方工具操作外,Android Studio 本身也提供了 Database Inspector 工具,可以直接在 IDE 中可视化地查看和修改数据库内容,无需导出文件,非常方便!

小马快跑的博客 2143

ROS 2在自动驾驶中的应用:感知节点开发

ROS 2在自动驾驶中的应用:感知节点开发 ,人工智能,计算机视觉,大模型,AI,本文围绕ROS 2在自动驾驶感知节点开发展开,介绍了ROS 2基础、感知节点开发流程,包括环境搭建、代码编写等,还阐述了常用传感器感知节点开发、多传感器融合,以及测试调试、性能优化、部署集成等内容,分析了开发面临的挑战与未来趋势,为相关开发提供了全面指导,涉及简单代码示例和概念解释。

不踩坑,不知道坑有多深;不总结,踩过的坑白踩。 14万+

Android之 常用数据库框架整理

4.2 ORM 框架,即 Object-Relational Mapping,它的作用是在关系型数据库和对象之间作一个映射,这样,我们在具体操作数据库的时候,就不需要再去和复杂的 SQL 语句打交道,只是像平时操作对象一样操作它就可以了。在数据库方面,它是主键。DaoSession还提供了一些通用的持久性方法,如实体的插入,加载,更新,刷新和删除。3.2 SQLiteOpenHelper的使用,自定义DatabaseHelper,继承SQLiteOpenHelper,来管理数据库的创建和数据库表的创建。

hdulhb的博客 6017

告别 GENERATE_SUBPOOL_DIR_FULL:用 RTTC 平替 CL_ALV_TABLE_CREATE=>CREATE_DYNAMIC_TABLE 的一套更稳方案

文章摘要:本文探讨了ABAP开发中动态内表的创建问题,重点分析了使用CL_ALV_TABLE_CREATE方法可能遇到的GENERATE_SUBPOOL_DIR_FULL错误。该错误源于临时subroutine pool的36次创建上限,常在批量处理或频繁调用时出现。文章提出基于RTTC技术的替代方案ZCL_ALV_TABLE_CREATE_RTTC,通过运行时类型服务直接创建动态内表,无需生成临时代码,从而规避了资源限制。该方法保持接口兼容性,只需简单替换类名即可实现无缝迁移,是解决动态表创建瓶颈的有效方

2007 年 ~ 2025 年,深耕 SAP 技术 18 年 223

OceanSim: 基于Isaac Sim GPU 加速水下机器人感知仿真框架

OceanSim 采用先进的基于物理的渲染技术,对水下视觉和声学传感器进行精确建模。与其他模拟引擎相比,OceanSim 的渲染速度要快得多。作为 NVIDIA Issac Sim 的扩展,OceanSim 采用了多功能设计。通过融入快速发展的 NVIDIA Omniverse 生态系统,我们的模拟器自然而然地在机器人学习和水下机器人技术之间架起了一座桥梁,从而促进了水下应用中体现型人工智能技术的开发和部署。OceanSim 将以开放源码的方式提供,使研究界能够以合作的模式作出贡献。

机器人控制与仿真应用 2048
上一篇: powerDesigner绘制类图
下一篇: java中并发常用工具类
zhoushenxian
博客等级 码龄12年 453粉丝 549原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值