暮酷酷来教下我

暮酷酷来教下我

<resultMap id="manyToOne" type="com.imooc.entity.Product">
    <id property="pid" column="pid"/>
    <result property="cid" column="cid"/>
    <association property="category" select="category.selectCategoryById" column="cid"/>
</resultMap>
<select id="manyToOne" resultMap="manyToOne">
    select * from shop.product limit 5
</select>

老师我说下我的理解,望老师帮忙指正:

通过主查询语句select * from shop.product limit 5,将查询到的结果封装到com.imooc.entity.Product中,其中实体类的变量与表中列名一致或符合驼峰命名法时,<result>标签的内容可以不写。

<association property="category" select="category.selectCategoryById" column="cid"/>,是将从表中查出来的 column="cid"值作为参数传入select="category.selectCategoryById"中,用此查询语句查出的结果封装到实体类的property="category"中。

我的疑问:关联查询的<association><collection>标签中,至少要有property、select、column三个属性吗?或者说一定要有它们吗?不想死记视频老师的方法,希望灵活应用

还有一点疑惑是<resultMap>标签中,主键一定要写在<id>标签里吗?写到result标签中行不行,写了会有什么影响吗?谢谢

正在回答

登陆购买课程后可参与讨论,去登陆

5回答

同学你好,

1、通过主查询语句select * from shop.product limit 5,将查询到的结果封装到com.imooc.entity.Product中,其中实体类的变量与表中列名一致或符合驼峰命名法时,<result>标签的内容可以不写。

<association property="category" select="category.selectCategoryById" column="cid"/>,是将从表中查出来的 column="cid"值作为参数传入select="category.selectCategoryById"中,用此查询语句查出的结果封装到实体类的property="category"中。

对于同学上面的理解是正确的,没有问题的。

2、关联查询的<association><collection>标签中,至少要有property、select、column三个属性吗?或者说一定要有它们吗?不想死记视频老师的方法,希望灵活应用

在<association>和<collection>的关联查询中,这些属性都是需要根据具体的情况选择使用的,

例如:

property :表示如果需要映射到列结果的字段或属性。用来匹配的 JavaBean 存在给定名字的属性,那么它将会被使用。

column:表示数据库中的列名,或者是列的别名。 用于传入嵌套的sql语句中。 

select:当需要进行执行另一个返回的映射SQL语句 ,进行嵌套查询时使用。

在实际开发中column可以不是必须编写的,因为如果sql不需要参数的话就不用给column,建议同学灵活运用每一个属性。

3、还有一点疑惑是<resultMap>标签中,主键一定要写在<id>标签里吗?写到result标签中行不行,写了会有什么影响吗?谢谢

是的,主键要编写在id标签中,id代表resultMap的主键,而result代表其属性。

在MyBatis中,如果主键编写在result中,可能会造成性能的问题,因为id 元素表示的结果将是对象的标识属性, 这样可以提高整体的性能,尤其是进行缓存和嵌套结果映射(也就是连接映射)的时候。同学记住就可以啦,这也可以理解是MyBatis这样设计的。

如果我的回答解决了你的疑惑,请采纳!祝学习愉快!

  • qq_粽翎_0 提问者 #1
    谢谢酷酷的解答,老师说关联查询的关联标签中如果调用的sql不需要参数的话就不用给column,我试了一下我的程序出错了,酷酷帮忙看下,我贴到回答区了
    2020-01-05 12:48:24
好帮手慕酷酷 2020-01-05 13:41:07

同学你好,同学这样编写sql语句是不正确的,不符合关联查询的含义哦,同学使用 两个sql语句并没有使他们进行关联,所以使用collection是不正确的,也就没有意义了。

老师这里所描述的含义是,因为在老师的案例中是分步进行嵌套查询,所以是一定需要column属性,因为在一个sql语句中查询出来的字段,然后需要使用到另一个sql中,根据上一个sql的执行后的参数,进行这个语句的查询,所以老师的案例中一定是需要使用column,进行传递参数的,而如果不使用分步进行嵌套查询,而是用一个sql进行关联查询就不需要使用到column了。

关于特定的编辑器就提交不了回答,老师这边会进行反馈的。同学也可以多尝试刷新一下页面。

如果我的回答解决了你的疑惑,请采纳!祝学习愉快!


  • 提问者 qq_粽翎_0 #1
    哦哦哦是这样,不过老师说的是联合查询吧,一条查询语句把多个表联合起来一起查询。那这样的话老师在你上一个回答中可能误解了我的意思了。我是问在利用关联查询,这是前提,所用到的<association>和<collection>标签里面,property和select和colum三个属性都是必须填写的是这样吗?
    2020-01-05 13:50:31
  • 好帮手慕酷酷 回复 提问者 qq_粽翎_0 #2
    同学你好,是的,如果按照同学上述描述的内容,是的都需要填写的。如果我的回答解决了你的疑惑,请采纳!祝学习愉快!
    2020-01-05 13:52:42
  • 提问者 qq_粽翎_0 回复 好帮手慕酷酷 #3
    最后啰嗦一句哈哈,<association>和<collection>里面的select属性,一定要用到外层查询语句所传递的参数才能进行查询吗?如果select里面的查询语句没有设置参数,是确定的查询结果,这个结果不能直接赋值给property实体类变量吗?
    2020-01-05 14:01:25
提问者 qq_粽翎_0 2020-01-05 13:27:17
@org.junit.Test
public void Test1() {
    SqlSession sqlSession = null;
    try {
        sqlSession = MybatisUtil.openSession();
        Category category = sqlSession.selectOne("category.oneToMany");
        System.out.println(category);
        System.out.println("=================================");
        for (Product product : category.getProducts()) {
            System.out.println(product);
        }
    } catch (Exception e) {
        e.printStackTrace();
    }finally {
        MybatisUtil.closeSqlSession(sqlSession);
    }
}

报错信息:

12:41:43.386 [main] DEBUG org.apache.ibatis.logging.LogFactory - Logging initialized using 'class org.apache.ibatis.logging.slf4j.Slf4jImpl' adapter.
12:41:44.091 [MLog-Init-Reporter] INFO com.mchange.v2.log.MLog - MLog clients using slf4j logging.
12:41:44.194 [MLog-Init-Reporter] DEBUG com.mchange.v2.log.MLog - Reading VM config for path list /com/mchange/v2/log/default-mchange-log.properties, /mchange-commons.properties, /c3p0.properties, hocon:/reference,/application,/c3p0,/, /mchange-log.properties, /
12:41:44.194 [MLog-Init-Reporter] DEBUG com.mchange.v2.log.MLog - The configuration file for resource identifier '/mchange-commons.properties' could not be found. Skipping.
12:41:44.194 [MLog-Init-Reporter] DEBUG com.mchange.v2.log.MLog - The configuration file for resource identifier '/c3p0.properties' could not be found. Skipping.
12:41:44.194 [MLog-Init-Reporter] DEBUG com.mchange.v2.log.MLog - The configuration file for resource identifier 'hocon:/reference,/application,/c3p0,/' could not be found. Skipping.
12:41:44.194 [MLog-Init-Reporter] DEBUG com.mchange.v2.log.MLog - The configuration file for resource identifier '/mchange-log.properties' could not be found. Skipping.
12:41:44.201 [main] DEBUG com.mchange.v2.cfg.MConfig - The configuration file for resource identifier '/mchange-commons.properties' could not be found. Skipping.
12:41:44.201 [main] DEBUG com.mchange.v2.cfg.MConfig - The configuration file for resource identifier '/mchange-log.properties' could not be found. Skipping.
12:41:44.201 [main] DEBUG com.mchange.v2.cfg.MConfig - The configuration file for resource identifier 'hocon:/reference,/application,/c3p0,/' could not be found. Skipping.
12:41:44.201 [main] DEBUG com.mchange.v2.cfg.MConfig - The configuration file for resource identifier '/c3p0.properties' could not be found. Skipping.
12:41:49.416 [main] INFO com.mchange.v2.c3p0.C3P0Registry - Initializing c3p0-0.9.5.4 [built 23-March-2019 23:00:48 -0700; debug? true; trace: 10]
12:41:50.264 [main] DEBUG com.mchange.v2.c3p0.management.DynamicPooledDataSourceManagerMBean - MBean: com.mchange.v2.c3p0:type=PooledDataSource,identityToken=1hgefpda7w6s47hc7c4b0|cb51256,name=1hgefpda7w6s47hc7c4b0|cb51256 registered.
12:41:50.936 [main] DEBUG com.mchange.v2.c3p0.management.DynamicPooledDataSourceManagerMBean - MBean: com.mchange.v2.c3p0:type=PooledDataSource,identityToken=1hgefpda7w6s47hc7c4b0|cb51256,name=1hgefpda7w6s47hc7c4b0|cb51256 unregistered, in order to be reregistered after update.
12:41:50.936 [main] DEBUG com.mchange.v2.c3p0.management.DynamicPooledDataSourceManagerMBean - MBean: com.mchange.v2.c3p0:type=PooledDataSource,identityToken=1hgefpda7w6s47hc7c4b0|cb51256,name=1hgefpda7w6s47hc7c4b0|cb51256 registered.

java.lang.NoClassDefFoundError: Could not initialize class com.imooc.utils.MybatisUtil

	at com.imooc.Test.Test1(Test.java:33)
	at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
	at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
	at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
	at java.lang.reflect.Method.invoke(Method.java:498)
	at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:50)
	at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:12)
	at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:47)
	at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:17)
	at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:325)
	at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:78)
	at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:57)
	at org.junit.runners.ParentRunner$3.run(ParentRunner.java:290)
	at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:71)
	at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:288)
	at org.junit.runners.ParentRunner.access$000(ParentRunner.java:58)
	at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:268)
	at org.junit.runners.ParentRunner.run(ParentRunner.java:363)
	at org.junit.runner.JUnitCore.run(JUnitCore.java:137)
	at com.intellij.junit4.JUnit4IdeaTestRunner.startRunnerWithArgs(JUnit4IdeaTestRunner.java:68)
	at com.intellij.rt.execution.junit.IdeaTestRunner$Repeater.startRunnerWithArgs(IdeaTestRunner.java:47)
	at com.intellij.rt.execution.junit.JUnitStarter.prepareStreamsAndStart(JUnitStarter.java:242)
	at com.intellij.rt.execution.junit.JUnitStarter.main(JUnitStarter.java:70)


  • 提问者 qq_粽翎_0 #1
    老师,这个MybatisUtil工具类是没问题的,我在执行其他SQL时都能正常运行
    2020-01-05 13:28:21
提问者 qq_粽翎_0 2020-01-05 13:22:44

<select id="selectProductByCid"  resultType="com.imooc.entity.Product">
   select * from product where cid = 1
</select>


<resultMap id="oneToMany" type="com.imooc.entity.Category">
   <id property="cid" column="cid"/>
   <collection property="products" select="product.selectProductByCid"/>
</resultMap>
<select id="oneToMany" resultMap="oneToMany">
   select * from category where cid = 1;
</select>


老师看看我写的没有参数的方式对不对

  • 提问者 qq_粽翎_0 #1
    是不是慕课网出问题了啊,我用特定的编辑器就提交不了回答,只能用普通文本提交了
    2020-01-05 13:23:56
  • 提问者 qq_粽翎_0 #2
    上面的两个查询标签是在两个xml文件里的,忘记说了,他们不在一起
    2020-01-05 13:25:33
提问者 qq_粽翎_0 2020-01-05 13:12:38
问题已解决,确定采纳
还有疑问,暂不采纳

恭喜解决一个难题,获得1积分~

来为老师/同学的回答评分吧

0 星

相似问题

登录后可查看更多问答,登录/注册

请稍等 ...
微信客服

购课补贴
联系客服咨询优惠详情

帮助反馈 APP下载

慕课网APP
您的移动学习伙伴

公众号

扫描二维码
关注慕课网微信公众号

在线咨询

领取优惠

免费试听

领取大纲

扫描二维码,添加
你的专属老师