前两天,用ormlite对单张表进行了基本的操作,但是,我们知道通常情况对于单张表格进行操作在实际情况中很前两天不现实,那么ormlite能否像Hibenate那样实现多张表之间的一对多,多对多(即OneToMany,ManyToMany)的关系映射呢?带着这个疑问,通过看了官方的文档,发现确实能够实现。先来看看One2Many这种情况的实现。

我在之前的demo基础上修改了一下,假设用户和部门之间的关系为多对一,即一个部门对应着多个用户,而一个用户只属于一个部门。同样先将运行效果图贴出来。

在我前面的文章中已经对中间的某些注解及类做了解释这里就不重复了,如有不懂的请先参考: android对象关系映射框架ormlite学习,这里就直接上代码了,说明就放到了代码中了。

用户类User.java

  1. <span style="font-size:18px;">@DatabaseTable(tableName = "tb_user")
  2. public class User {
  3. //用户编号
  4. @DatabaseField(generatedId=true)
  5. private int userId;
  6. //用户名
  7. @DatabaseField
  8. private String userName;
  9. //密码
  10. @DatabaseField
  11. private int age;
  12. //入职时间
  13. @DatabaseField(format="DATE_STRING")
  14. private Date date;
  15. //用户所属部门
  16. /**
  17. * foreign = true:说明这是一个外部引用关系
  18. * foreignAutoRefresh = true:当对象被查询时,外部属性自动刷新(暂时我也没看懂其作用)
  19. *
  20. */
  21. @DatabaseField(foreign = true,foreignAutoRefresh = true)
  22. private Dept dept;
  23. public User() {
  24. //提供无参构造函数,这样查询的时候可以返回查询出来的对象
  25. }
  26. public User( int userId,String userName, int age) {
  27. this.userId = userId;
  28. this.userName = userName;
  29. this.age = age;
  30. }
  31. get/set方法……
  32. }
  33. </span>

部门类Dept.java

  1. <span style="font-size:18px;">/**
  2. * 部门(这里假设一个用户只对应一个部门,而一个部门对应着多个用户,即一对多的关系)
  3. * @author leox
  4. *
  5. */
  6. @DatabaseTable(tableName="tb_dept")
  7. public class Dept {
  8. //部门编号
  9. @DatabaseField(generatedId=true)
  10. private int deptId;
  11. //部门名称
  12. @DatabaseField
  13. private String deptName;
  14. //用户信息集合
  15. @ForeignCollectionField
  16. /**
  17. * 这里需要注意的是:属性类型只能是ForeignCollection<T>或者Collection<T>
  18. * 如果需要懒加载(延迟加载)可以在@ForeignCollectionField加上参数eager=false
  19. * 这个属性也就说明一个部门对应着多个用户
  20. */
  21. private ForeignCollection<User> users;
  22. public Dept(){
  23. }
  24. public Dept(int deptId,String deptName){
  25. this.deptId = deptId;
  26. this.deptName = deptName;
  27. }
  28. Get()/set()方法……
  29. }
  30. </span>

SqlliteOpenHelper类:

  1. <span style="font-size:18px;">public class DatabaseHelper extends OrmLiteSqliteOpenHelper{
  2. // 数据库名称
  3. private static final String DATABASE_NAME = "helloAndroid.db";
  4. // 数据库version
  5. private static final int DATABASE_VERSION = 1;
  6. /**
  7. * 包含两个泛型:
  8. * 第一个泛型表DAO操作的类
  9. * 第二个表示操作类的主键类型
  10. */
  11. private Dao<User, Integer> userDao = null;
  12. private Dao<Dept,Integer> deptDao = null;
  13. private RuntimeExceptionDao<User, Integer> simpleRuntimeUserDao = null;
  14. private RuntimeExceptionDao<Dept, Integer> simpleRuntimeDeptDao = null;
  15. public DatabaseHelper(Context context) {
  16. super(context, DATABASE_NAME, null, DATABASE_VERSION);
  17. }
  18. @Override
  19. public void onCreate(SQLiteDatabase sqliteDatabase, ConnectionSource connectionSource) {
  20. try {
  21. Log.i(DatabaseHelper.class.getName(), "onCreate");
  22. Log.i("test", "name = "+DatabaseHelper.class.getName());
  23. TableUtils.createTable(connectionSource, Dept.class);
  24. TableUtils.createTable(connectionSource, User.class);
  25. } catch (SQLException e) {
  26. Log.e(DatabaseHelper.class.getName(), "Can't create database", e);
  27. throw new RuntimeException(e);
  28. }
  29. }
  30. /**
  31. * 插入一条用户数据
  32. */
  33. public void insert(User user){
  34. RuntimeExceptionDao<User, Integer> dao = getSimpleDataUserDao();
  35. //通过实体对象创建在数据库中创建一条数据,成功返回1,说明插入了一条数据
  36. Log.i("test", "dao = " + dao+"  user= "+user);
  37. int returnValue = dao.create(user);
  38. Log.i("test", "插入数据后返回值:"+returnValue);
  39. }
  40. /**
  41. * 查询所有的用户信息
  42. * @return
  43. */
  44. public List<User> findAllUser(){
  45. RuntimeExceptionDao<User, Integer> dao = getSimpleDataUserDao();
  46. return dao.queryForAll();
  47. }
  48. public RuntimeExceptionDao<User, Integer> getSimpleDataUserDao() {
  49. if (simpleRuntimeUserDao == null) {
  50. simpleRuntimeUserDao = getRuntimeExceptionDao(User.class);
  51. }
  52. Log.i("test", "simpleRuntimeDao ======= "+simpleRuntimeUserDao);
  53. return simpleRuntimeUserDao;
  54. }
  55. /**
  56. * 这个方法在你的应用升级以及它有一个更高的版本号时调用。所以需要你调整各种数据来适应新的版本
  57. */
  58. @Override
  59. public void onUpgrade(SQLiteDatabase sqliteDatabase, ConnectionSource connectionSource, int oldVersion,
  60. int newVersion) {
  61. Log.i("test", "更新....");
  62. try {
  63. Log.i(DatabaseHelper.class.getName(), "onUpgrade");
  64. //删掉旧版本的数据
  65. TableUtils.dropTable(connectionSource, User.class, true);
  66. TableUtils.dropTable(connectionSource, Dept.class, true);
  67. //创建一个新的版本
  68. onCreate(sqliteDatabase, connectionSource);
  69. } catch (SQLException e) {
  70. Log.e(DatabaseHelper.class.getName(), "Can't drop databases", e);
  71. throw new RuntimeException(e);
  72. }
  73. }
  74. public Dao<User, Integer> getDao() throws SQLException {
  75. if (userDao == null) {
  76. userDao = getDao(User.class);
  77. }
  78. return userDao;
  79. }
  80. /***************************************以下为部门操作******************************************/
  81. public Dao<Dept, Integer> getDeptDao() throws SQLException {
  82. if (deptDao == null) {
  83. deptDao = getDao(Dept.class);
  84. }
  85. return deptDao;
  86. }
  87. public RuntimeExceptionDao<Dept, Integer> getSimpleDataDeptDao() {
  88. if (simpleRuntimeDeptDao == null) {
  89. simpleRuntimeDeptDao = getRuntimeExceptionDao(Dept.class);
  90. }
  91. Log.i("test", "simpleRuntimeDaodeptdept ======= "+simpleRuntimeDeptDao);
  92. return simpleRuntimeDeptDao;
  93. }
  94. /**
  95. * 插入一条部门数据
  96. */
  97. public void insertDept(Dept dept){
  98. RuntimeExceptionDao<Dept, Integer> dao = getSimpleDataDeptDao();
  99. //通过实体对象创建在数据库中创建一条数据,成功返回1,说明插入了一条数据
  100. Log.i("test", "dao = " + dao+"  dept= "+dept.getDeptName());
  101. int returnValue = dao.create(dept);
  102. Log.i("test", "插入数据后返回值:"+returnValue);
  103. }
  104. /**
  105. * 查询所有的部门信息
  106. * @return
  107. */
  108. public List<Dept> findAllDept(){
  109. RuntimeExceptionDao<Dept, Integer> dao = getSimpleDataDeptDao();
  110. return dao.queryForAll();
  111. }
  112. public Dept findByDeptId(int deptId){
  113. RuntimeExceptionDao<Dept, Integer> dao = getSimpleDataDeptDao();
  114. return dao.queryForId(deptId);
  115. }
  116. }
  117. </span>

RegistActivity类:(这个类是模拟了员工录入,输入员工信息和所属部门)

  1. <span style="font-size:18px;">/**
  2. * 员工信息录入
  3. * @author leox
  4. *
  5. */
  6. public class RegistActivity  extends Activity {
  7. EditText userNameEdit;//用户名编辑框
  8. EditText ageEdit;//年龄编辑框
  9. EditText hiredateEdit;//入职时间编辑框
  10. EditText deptEdit;//部门编辑框
  11. Button reButton;//提交按钮
  12. DatabaseHelper helper = new DatabaseHelper(this);
  13. @Override
  14. protected void onCreate(Bundle savedInstanceState) {
  15. super.onCreate(savedInstanceState);
  16. setContentView(R.layout.activity_main);
  17. userNameEdit = (EditText)this.findViewById(R.id.et_username);
  18. ageEdit = (EditText)this.findViewById(R.id.et_age);
  19. hiredateEdit = (EditText)this.findViewById(R.id.et_date);
  20. deptEdit = (EditText)this.findViewById(R.id.et_dept);
  21. reButton = (Button)this.findViewById(R.id.btn_regist);
  22. reButton.setOnClickListener(new myClickListener());
  23. }
  24. @Override
  25. public boolean onCreateOptionsMenu(Menu menu) {
  26. getMenuInflater().inflate(R.menu.main, menu);
  27. return true;
  28. }
  29. class myClickListener implements OnClickListener{
  30. @Override
  31. public void onClick(View v) {
  32. //用户名
  33. String userName = userNameEdit.getText().toString();
  34. //年龄
  35. String age = ageEdit.getText().toString();
  36. String da = hiredateEdit.getText().toString();
  37. //入职时间
  38. DateFormat df = new SimpleDateFormat("yyyy-MM-dd");
  39. Date hiredate=null;
  40. try {
  41. hiredate = df.parse(da);
  42. } catch (ParseException e) {
  43. e.printStackTrace();
  44. }
  45. Log.i("test", "date = "+hiredate);
  46. //部门信息
  47. String deptName = deptEdit.getText().toString();
  48. List<Dept> depts = helper.findAllDept();
  49. Dept dept = null;
  50. //查询出所有的部门信息,如果输入的部门名数据库中不存在那就创建一条新的记录,如果存在则采用原有
  51. if(depts.size()>0){
  52. for(Dept d:depts){
  53. if(d.getDeptName().equals(deptName)){
  54. dept = d;
  55. }else{
  56. dept = new Dept();
  57. dept.setDeptName(deptName);
  58. //插入部门信息
  59. helper.insertDept(dept);
  60. }
  61. }
  62. }else{
  63. dept = new Dept();
  64. dept.setDeptName(deptName);
  65. //插入部门信息
  66. helper.insertDept(dept);
  67. }
  68. //用户信息
  69. User user = new User();
  70. user.setUserName(userName);
  71. user.setAge(Integer.parseInt(age));
  72. user.setDate(hiredate);
  73. user.setDept(dept);
  74. //插入用户信息
  75. helper.insert(user);
  76. Intent intent = new Intent();
  77. intent.setClass(RegistActivity.this, MainActivity.class);
  78. startActivity(intent);
  79. }
  80. }
  81. }
  82. </span>

对应的布局文件:activity_main.xml

  1. <span style="font-size:18px;"><LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
  2. xmlns:tools="http://schemas.android.com/tools"
  3. android:layout_width="match_parent"
  4. android:layout_height="match_parent"
  5. android:paddingBottom="@dimen/activity_vertical_margin"
  6. android:paddingLeft="@dimen/activity_horizontal_margin"
  7. android:paddingRight="@dimen/activity_horizontal_margin"
  8. android:paddingTop="@dimen/activity_vertical_margin"
  9. android:orientation="vertical"
  10. android:gravity="center"
  11. tools:context=".RegistActivity" >
  12. <TextView
  13. android:layout_width="wrap_content"
  14. android:layout_height="wrap_content"
  15. android:textSize="20dp"
  16. android:text="员工信息录入" />
  17. <LinearLayout
  18. android:layout_width="fill_parent"
  19. android:layout_height="wrap_content"
  20. android:gravity="center"
  21. android:orientation="horizontal">
  22. <TextView
  23. android:layout_width="wrap_content"
  24. android:layout_height="wrap_content"
  25. android:text="用户名:"/>
  26. <EditText
  27. android:id="@+id/et_username"
  28. android:layout_width="200px"
  29. android:layout_height="wrap_content" />
  30. </LinearLayout>
  31. <LinearLayout
  32. android:layout_width="fill_parent"
  33. android:layout_height="wrap_content"
  34. android:gravity="center"
  35. android:orientation="horizontal">
  36. <TextView
  37. android:layout_width="wrap_content"
  38. android:layout_height="wrap_content"
  39. android:text="年龄:"/>
  40. <EditText
  41. android:id="@+id/et_age"
  42. android:layout_width="200px"
  43. android:layout_height="wrap_content"/>
  44. </LinearLayout>
  45. <LinearLayout
  46. android:layout_width="fill_parent"
  47. android:layout_height="wrap_content"
  48. android:gravity="center"
  49. android:orientation="horizontal">
  50. <TextView
  51. android:layout_width="wrap_content"
  52. android:layout_height="wrap_content"
  53. android:text="入职时间:"/>
  54. <EditText
  55. android:id="@+id/et_date"
  56. android:layout_width="200px"
  57. android:layout_height="wrap_content"/>
  58. </LinearLayout>
  59. <LinearLayout
  60. android:layout_width="fill_parent"
  61. android:layout_height="wrap_content"
  62. android:gravity="center"
  63. android:orientation="horizontal">
  64. <TextView
  65. android:layout_width="wrap_content"
  66. android:layout_height="wrap_content"
  67. android:text="部门:"/>
  68. <EditText
  69. android:id="@+id/et_dept"
  70. android:layout_width="200px"
  71. android:layout_height="wrap_content"/>
  72. </LinearLayout>
  73. <Button
  74. android:id="@+id/btn_regist"
  75. android:layout_width="wrap_content"
  76. android:layout_height="wrap_content"
  77. android:text="提交"/>
  78. </LinearLayout>
  79. </span>

MainActivity.java类,这个类用来操作员工信息录入按钮,以及显示员工信息按钮的操作

  1. <span style="font-size:18px;">public class MainActivity extends Activity {
  2. Button button1;//员工信息录入按钮
  3. Button button2;//员工信息显示按钮
  4. TextView textView;//用来显示查询到的用户信息
  5. DatabaseHelper helper = new DatabaseHelper(this);
  6. @Override
  7. protected void onCreate(Bundle savedInstanceState) {
  8. super.onCreate(savedInstanceState);
  9. setContentView(R.layout.main);
  10. button1 = (Button)this.findViewById(R.id.main_btn_inputinfo);
  11. button2 = (Button)this.findViewById(R.id.main_btn_show);
  12. textView = (TextView)this.findViewById(R.id.main_show_user);
  13. //点击注册按钮跳转到注册页面
  14. button1.setOnClickListener(new OnClickListener() {
  15. @Override
  16. public void onClick(View v) {
  17. Intent intent = new Intent();
  18. intent.setClass(MainActivity.this, RegistActivity.class);
  19. startActivity(intent);
  20. }
  21. });
  22. //点击“显示”按钮跳转到用户信息显示页面并将注册用户信息显示出来
  23. button2.setOnClickListener(new OnClickListener() {
  24. @Override
  25. public void onClick(View v) {
  26. List<Dept> list = helper.findAllDept();
  27. Log.i("test", "有没有部门?----------------"+list.size());
  28. Dept dept = null;
  29. if(list.size()>0){
  30. dept = helper.findByDeptId(list.get(0).getDeptId());
  31. ForeignCollection<User> orders = dept.getUsers();
  32. CloseableIterator<User> iterator = orders.closeableIterator();
  33. String str = dept.getDeptName()+" 部门下有以下职员:";
  34. try {
  35. while(iterator.hasNext()){
  36. User user = iterator.next();
  37. str+=user.getUserId()+"号:"+user.getUserName()+" 年龄:"+user.getAge()+"  受雇日期: "+user.getDate()+"   ";
  38. }
  39. } finally {
  40. try {
  41. iterator.close();
  42. } catch (SQLException e) {
  43. e.printStackTrace();
  44. }
  45. }
  46. textView.setText(str);
  47. }else{
  48. textView.setText("亲!还没有部门吧!");
  49. }
  50. }
  51. });
  52. }
  53. @Override
  54. public boolean onCreateOptionsMenu(Menu menu) {
  55. // Inflate the menu; this adds items to the action bar if it is present.
  56. getMenuInflater().inflate(R.menu.main, menu);
  57. return true;
  58. }
  59. }
  60. </span>

对应的布局文件:main.xml

  1. <span style="font-size:18px;"><LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
  2. xmlns:tools="http://schemas.android.com/tools"
  3. android:layout_width="match_parent"
  4. android:layout_height="match_parent"
  5. android:paddingBottom="@dimen/activity_vertical_margin"
  6. android:paddingLeft="@dimen/activity_horizontal_margin"
  7. android:paddingRight="@dimen/activity_horizontal_margin"
  8. android:paddingTop="@dimen/activity_vertical_margin"
  9. android:orientation="vertical"
  10. android:gravity="center"
  11. tools:context=".MainActivity" >
  12. <Button
  13. android:id="@+id/main_btn_inputinfo"
  14. android:layout_width="wrap_content"
  15. android:layout_height="wrap_content"
  16. android:text="员工信息录入"/>
  17. <Button
  18. android:id="@+id/main_btn_show"
  19. android:layout_width="wrap_content"
  20. android:layout_height="wrap_content"
  21. android:text="员工信息显示"/>
  22. <!-- <Button
  23. android:id="@+id/main_btn_delete"
  24. android:layout_width="wrap_content"
  25. android:layout_height="wrap_content"
  26. android:text="删除"/>
  27. <Button
  28. android:id="@+id/main_btn_deleteAll"
  29. android:layout_width="wrap_content"
  30. android:layout_height="wrap_content"
  31. android:text="批量删除"/> -->
  32. <TextView
  33. android:id="@+id/main_show_user"
  34. android:layout_width="wrap_content"
  35. android:layout_height="wrap_content"/>
  36. </LinearLayout>
  37. </span>

android对象关系映射框架ormlite之一对多(OneToMany)的更多相关文章

  1. Android数据库框架——GreenDao轻量级的对象关系映射框架,永久告别sqlite

    Android数据库框架--GreenDao轻量级的对象关系映射框架,永久告别sqlite 前不久,我在写了ORMLite这个框架的博文 Android数据库框架--ORMLite轻量级的对象关系映射 ...

  2. Hibernate(开放源代码的对象关系映射框架)

    Hibernate是一个开放源代码的对象关系映射框架,它对JDBC进行了非常轻量级的对象封装,它将POJO与数据库表建立映射关系,是一个全自动的orm框架,hibernate可以自动生成SQL语句,自 ...

  3. JavaEE之Hibernate(开放源代码的对象关系映射框架)

    Hibernate(开放源代码的对象关系映射框架) 1.简介 Hibernate是一个开放源代码的对象关系映射框架,它对JDBC进行了非常轻量级的对象封装,它将POJO与数据库表建立映射关系,是一个全 ...

  4. 解析大型.NET ERP系统数据访问 对象关系映射框架LLBL Gen Pro

    LLBL Gen Pro是一个为.NET开发人员设计的的对象关系映射(ORM)框架,与NHibernate,Entity Framework等框架一样,通过实体与数据表的映射,实现关系数据库持久化. ...

  5. Hibernate (开源对象关系映射框架)

    一.基本介绍1.它对JDBC进行了非常轻量级的对象封装,它将POJO与数据库表建立映射关系,是一个全自动的orm(对象关系映射)框架,hibernate可以自动生成SQL语句,自动执行: Hibern ...

  6. 接触LLBL Gen Pro 对象关系映射框架后 前途变的一片光明

    时间回到2010年,那时候还是熟悉代码生成+基础框架这种模式,基本的开发思路是通过代码生成器生成实体,再生成接口与实现类,最后拖拉控件,写界面数据绑定代码.基本上就是动软代码生成器给出的模式,或是微软 ...

  7. ORM 对象关系映射

    ORM (object relation mapping) 就是将对象数据转换为sql语句并执行 对象关系映射框架 orm 需要做的事情 1 生成创建表的语句 2 插入数据的语句 3 删除数据的语句 ...

  8. Android数据库框架——ORMLite轻量级的对象关系映射(ORM)Java包

    Android数据库框架--ORMLite轻量级的对象关系映射(ORM)Java包 事实上,我想写数据库的念头已经很久了,在之前写了一个答题系统的小项目那只是初步的带了一下数据库,数据库是比较强大的, ...

  9. ORM框架(对象关系映射)

    Entity Framework 学习初级篇1--EF基本概况 http://www.cnblogs.com/xray2005/archive/2009/05/07/1452033.html ORM  ...

随机推荐

  1. linq 多条件查询

    Linq 进行多条件查询的时候使用PredicateBuilder帮助类可以很好的解决. 类的源码: public static class PredicateBuilder { /// <su ...

  2. Mysql基础2

    一.DQL下查询英语分数在 80-90之间的同学.mysql>SELECT * FROM student WHERE english>=80 AND english<=90;或者my ...

  3. 【java】:解析xml

    ==========================================xml文件<?xml version="1.0" encoding="GB231 ...

  4. 校验两次密码一致的js代码

    function checkpasswd(){ var passwd = document.getElementByIdx_x_x_xx_x('passwd').value; var repasswd ...

  5. C# 根据身份证号码获取简易信息

    public class PackIden { /// <summary> /// 根据身份证获取生日 /// </summary> /// <param name=&q ...

  6. 详解 Windows 8.1 下的按流量计费的使用

    用过 Windows 8 ,而且用过手机热点的同学应该都不陌生,Windows 会自动识别这个Wifi是按流量计费的.然后会限制流量. 在正式说怎么用之前,我们先啦讨论一下按流量计费网络. 有线网络无 ...

  7. mvc-servlet---servletContext与servletConfig2

    在编写servlet过程中,需要用到 ServletConfig.ServletContext对象,对这两种对象的介绍如下: ServletContext对象:servlet容器在启动时会加载web应 ...

  8. getUserMedia

    index.ejs getUserMedia()方法有三个参数: 1.约束对象 2.成功回调函数,传入参数:LocalMediaStream 3.失败回调函数,传入参数:error object &l ...

  9. Dynamic CRM 2013学习笔记(三十)Linq使用报错 A proxy type with the name account has been defined by another assembly

    在CRM中使用linq时,有时会报这个错误: A proxy type with the name account has been defined by another assembly. Curr ...

  10. ArcMap 连接SDE 出错“Failed to connect to the specified server. Entry for SDE instance no found in services file.”

    问题描述 环境: ARCMAP 10.0 ARCSDE FOR ORACLE 10.0   在通过用ArcMap 连接ORACLE SDE时出现上面的错.   解决方式 在 C:\Windows\Sy ...