MongoDB中_class字段的作用
我们知道,如果你用Java的Sping Data 框架映射Pojo为MongoDB数据时,数据库中会自动给你添加一个_class字段,那这个字段是干嘛用的呢?我们可以不可以不要这个字段呢?
直接上结论:答案其实很简答,这个字段就是用来映射Pojo的,更具体的说,是为了方便处理Pojo中存在继承的情况,增加系统的扩展性的,接下来上例子:
_class字段帮助映射子类
为了方便演示,这里用Spring Data 给我们提供的mongoTemplate来操作。有关mongoDB和Spring Data的环境我就不贴了,直接上测试代码:
拥有继承关系的实体类
@Document是把一个java类声明为mongodb的文档,可以通过collection参数指定这个类对应的文档。
父类Person
@Document(collection = "test")
public class Person {
protected String name;
protected int age;
//set/get方法
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
}
子类 Student
@Document(collection = "test")
public class Student extends Person {
String a;
String b;
@Override
public String toString() {
return "Student{" +
"name='" + name + '\'' +
", age=" + age +
", a='" + a + '\'' +
", b='" + b + '\'' +
'}';
}
public String getA() {
return this.a;
}
public void setA(String a) {
this.a = a;
}
public String getB() {
return this.b;
}
public void setB(String b) {
this.b = b;
}
}
Dao层
Dao接口
public interface PersonDao {
void addPerson(Person person);
Person findPersonByName(String name);
}
Dao实现
@Repository
public class PersonDapImpl implements PersonDao {
@Autowired
MongoTemplate mongoTemplate;
@Override
public void addPerson(Person person) {
mongoTemplate.save(person);
}
@Override
public Person findPersonByName(String name) {
Query query = new Query(Criteria.where("name").is(name));
Person person = mongoTemplate.findOne(query, Person.class);
return person;
}
}
测试方法
public class PersonDapImplTest extends BaseTest {
@Autowired
PersonDao personDao;
@Test
public void addPerson() {
Person person = new Person();
person.setName("张");
person.setAge(10);
personDao.addPerson(person);
}
@Test
public void addStudent() {
Student student = new Student();
student.setName("小张");
student.setAge(12);
student.setA("a");
student.setB("b");
personDao.addPerson(student);
}
@Test
public void findPerson() {
System.out.println("==============开始查找==============");
Person person = personDao.findPersonByName("小张");
System.out.println();
System.out.println();
System.out.println();
if (person != null) {
System.out.println(person.toString());
}else {
System.out.println("null");
}
}
}
测试结论
测试中,小张是张的子类,mongoDB中已经插入了2条数据:

查询小张,得到的类是Student类吗?

可以看到,最终展示的是Student的详细信息,说明_class能帮助我们反序列化出子类。
那如果去掉了_class列,会是什么样呢?
去掉_class
去掉_class的方法需要配置一下
需要配置MappingConverter:更详细的去掉_class的方法可以参考其他博文。
@Bean
public MappingMongoConverter mappingMongoConverter(MongoDbFactory factory,
MongoMappingContext context, BeanFactory beanFactory, CustomConversions conversions) {
DbRefResolver dbRefResolver = new DefaultDbRefResolver(factory);
MappingMongoConverter mappingConverter = new MappingMongoConverter(dbRefResolver, context);
// remove _class field
// mappingConverter.setTypeMapper(new DefaultMongoTypeMapper(null));
mappingConverter.setCustomConversions(conversions);
return mappingConverter;
}
去掉_class后:

再次查询"小张"

可以看到,mongoDB无法帮助我们来映射子类了。返回的数据被反序列化成了Person类。
MongoDB中_class字段的作用的更多相关文章
- mongodb使用_遍历列表中的元素,作为变量,循环修改mongodb中的字段
一.问题描述: 需要将工作界面上的一些已经离职的用户状态改为失效,并备注为离职 二.需要准备/拿到手的工具/条件/数据: 1.已离职人员名单(excel格式) 2.任意mongodb工具(笔者使用的是 ...
- MongoDB中的字段类型Id
众所周知,在向MongoDB的集合中添加一条记录时,系统会自动增加一个字段名为"_id",类型为ObjectId的字段,其值为24位字符串,可以使用此值作为记录的唯一标识. 项目中 ...
- 集合类中modCount字段的作用
ArrayList.LinkedList.HashMap中都有一个字段叫modCount.这个字段的用途,在ArrayList的父类AbstractList源码中有注释,说的很清楚: /** * Th ...
- 【memcached】memcached中flags字段的作用
我们一般只注意到memcached的数据结构是key,value,今天看memcached源代码的时候,盯上了flags,没看明白.后来问了一下同事,说PHP当中使用flags标记,标识memcach ...
- maven中pom文件中name字段的作用
- spring mongodb中去掉_class列
调用mongoTemplate的save方法时, spring-data-mongodb的TypeConverter会自动给document添加一个_class属性, 值是你保存的类名. 这种设计并没 ...
- ABAP 数据字典中的参考表和参考字段的作用
ABAP数据字典中的参考表和参考字段的作用 大家最初在SE11中创建表和结构的时候都会遇到一个问题,如果设定了某个字段为QUAN或者CURR类型,也就是数量或金额的时候,总会要求输入一个参考 ...
- spring data mongodb中,如果对象中的属性不想加入到数据库字段中
spring data mongodb中,如果对象中的属性不想加入到数据库字段中,可加@Transient注解,声明为透明属性 spring data mongodb 官网帮助文档 http://ww ...
- SAP MM 物料主数据采购视图中的字段'Var. OUn'的作用?
SAP MM 物料主数据采购视图中的字段'Var. OUn'的作用? 物料主数据采购视图里有一个字段,叫做'Var. OUn'的, 如下图: 这个字段,笔者之前所参与的项目里,从来没有用过.所以,笔者 ...
随机推荐
- PowerBuilder编程新思维1:扩展(Lua)
前言 PowerBuilder作为开发工具退出一线行列已经很久了,在2019年来谈这样一款老旧的编程工具是否有意义?诚然,PB有着太多硬伤,但还是有它的用武之地的.而且今天讲的这个“新思维”大部分内容 ...
- .3-浅析webpack源码之预编译总览
写在前面: 本来一开始想沿用之前vue源码的标题:webpack源码之***,但是这个工具比较巨大,所以为防止有人觉得我装逼跑来喷我(或者随时鸽),加上浅析二字,以示怂. 既然是浅析,那么案例就不必太 ...
- Effective C++ 50条款
条款1:尽量用const和inline而不用#define 以const 行使常量折叠,用inline 代替常用操作的宏定义,而且库里面有很多常用函数可用.当然不能抛弃宏,宏还是很有用滴.偶最近才发现 ...
- redis缓存工具类,提供序列化接口
1.序列化工具类 package com.qicheshetuan.backend.util; import java.io.ByteArrayInputStream; import java.io. ...
- java8 集合神操作
public class StreamUtils { private static final List<Integer> listInteger = Lists.newArrayList ...
- Herding(hdu4709)三点运用行列式求面积
Herding Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)Total Submis ...
- 设计模式原则(6)--Open-Closed Principle(OCP)--开闭原则
作者QQ:1095737364 QQ群:123300273 欢迎加入! 1.定义: 一个软件实体应当对扩展开放,对修改关闭.即软件实体应尽量在不修改原有代码的情况下进行扩展. 2.使用场 ...
- AsnycLocal与ThreadLocal
AsnycLocal与ThreadLocal AsnyncLocal与ThreadLocal都是存储线程上下文的变量,但是,在实际使用过程中两者又有区别主要的表现在: AsyncLocal变量可以在父 ...
- Angular 实现Bootstrap ScrollSpy控件
Bootstap是基于JQuery开发,Angular中不支持Bootstrap相关事件逻辑.本文基于Typecript开发了一个Angular可用的ScrollSpy控件.Scrollspy控件主要 ...
- BZOJ4373: 算术天才⑨与等差数列(线段树 hash?)
题意 题目链接 Sol 正经做法不会,听lxl讲了一种很神奇的方法 我们考虑如果满足条件,那么需要具备什么条件 设mx为询问区间最大值,mn为询问区间最小值 mx - mn = (r - l) * k ...