Java 不使用ORM时,如何处理嵌套对象?
我正在改变Java中的ORM,我想知道在非ORM环境中处理多对一和多对一关系的最佳方式是什么 在我的Java 不使用ORM时,如何处理嵌套对象?,java,jdbc,orm,Java,Jdbc,Orm,我正在改变Java中的ORM,我想知道在非ORM环境中处理多对一和多对一关系的最佳方式是什么 在我的Customer.java类中,我有: private Long id; private String name; private Date dob; //About 10 more fields private List<Pet> pets; 我的宠物数据库表如下所示 id BIGSERIAL PRIMARY KEY, name VARCHAR(20), owner_id BIGS
Customer.java
类中,我有:
private Long id;
private String name;
private Date dob;
//About 10 more fields
private List<Pet> pets;
我的宠物数据库表如下所示
id BIGSERIAL PRIMARY KEY,
name VARCHAR(20),
owner_id BIGSERIAL REFERENCES...
现在我意识到,如果我运行一个连接两个表的查询,我会得到一个返回的“平面”数据结构,其中包含Customer
和Pet
的字段以及任何外键。在这种情况下,处理数据的常用/最有效的方法是什么
a。通过调用customer.setName(resultSet.getString((“name”))
…?b、 通过将返回的数据转换为
映射
,按原样使用返回的数据
数据流是:从数据库读取数据->呈现为JSON供AngularJS前端使用->将修改后的数据发送回服务器进行验证->应用域逻辑->保存到数据库。此时最好的选择是:
在所有这些情况下,您都会编写自己的sql查询,并且大多数情况下会生成联接查询。顺便说一句,您给出的示例不是嵌套对象。目前最好的选择是:
在所有这些情况下,您都会编写自己的sql查询,并且大多数情况下,它们会生成联接查询。顺便说一句,您给出的示例不是嵌套对象。如果您想在单个查询中同时读取Customer和Pet以获得更好的性能,可以执行以下操作:
List<Customer> customers = new ArrayList<>();
String sql = "SELECT c.id AS cust_id" +
", c.name AS cust_name" +
", c.dob AS cust_dob" +
", p.id AS pet_id" +
", p.name AS pet_name" +
" FROM Customer c" +
" LEFT JOIN Pet p ON p.owner_id = c.id" +
" WHERE c.name LIKE ?" +
" ORDER BY c.id";
try (PreparedStatement stmt = conn.prepareStatement(sql)) {
stmt.setString(1, "%DOE%");
try (ResultSet rs = stmt.executeQuery()) {
Customer customer = null;
while (rs.next()) {
long cust_id = rs.getLong("cust_id");
if (customer == null || customer.getId() != cust_id) {
customer = new Customer();
customer.setId(cust_id);
customer.setName(rs.getString("cust_name"));
customer.setDob(rs.getDate("cust_dob"));
customers.add(customer);
}
long pet_id = rs.getLong("pet_id");
if (pet_id != 0) {
Pet pet = new Pet();
pet.setId(pet_id);
pet.setName(rs.getString("pet_name"));
pet.setOwner(customer);
customer.addPet(pet);
}
}
}
}
List customers=new ArrayList();
String sql=“选择c.id作为客户id”+
,c.作为客户名称的名称+
,c.dob作为客户dob+
,p.id作为宠物id+
,p.name作为宠物名+
“来自客户c”+
“在p.owner\u id=c.id上左加入宠物p”+
“你的名字在哪里?”+
“凭身份证订购”;
try(PreparedStatement stmt=conn.prepareStatement(sql)){
stmt.setString(1,“%DOE%”);
try(ResultSet rs=stmt.executeQuery()){
客户=空;
while(rs.next()){
long cust_id=rs.getLong(“cust_id”);
if(customer==null | | customer.getId()!=cust_id){
客户=新客户();
customer.setId(cust_id);
customer.setName(rs.getString(“cust_name”);
customer.setDob(rs.getDate(“cust_-dob”);
客户。添加(客户);
}
long pet_id=rs.getLong(“pet_id”);
如果(宠物id!=0){
宠物=新宠物();
pet.setId(pet_id);
pet.setName(rs.getString(“pet_name”);
宠物主人(顾客);
customer.addPet(pet);
}
}
}
}
如果您想在单个查询中同时读取客户和宠物以获得更好的性能,可以执行以下操作:
List<Customer> customers = new ArrayList<>();
String sql = "SELECT c.id AS cust_id" +
", c.name AS cust_name" +
", c.dob AS cust_dob" +
", p.id AS pet_id" +
", p.name AS pet_name" +
" FROM Customer c" +
" LEFT JOIN Pet p ON p.owner_id = c.id" +
" WHERE c.name LIKE ?" +
" ORDER BY c.id";
try (PreparedStatement stmt = conn.prepareStatement(sql)) {
stmt.setString(1, "%DOE%");
try (ResultSet rs = stmt.executeQuery()) {
Customer customer = null;
while (rs.next()) {
long cust_id = rs.getLong("cust_id");
if (customer == null || customer.getId() != cust_id) {
customer = new Customer();
customer.setId(cust_id);
customer.setName(rs.getString("cust_name"));
customer.setDob(rs.getDate("cust_dob"));
customers.add(customer);
}
long pet_id = rs.getLong("pet_id");
if (pet_id != 0) {
Pet pet = new Pet();
pet.setId(pet_id);
pet.setName(rs.getString("pet_name"));
pet.setOwner(customer);
customer.addPet(pet);
}
}
}
}
List customers=new ArrayList();
String sql=“选择c.id作为客户id”+
,c.作为客户名称的名称+
,c.dob作为客户dob+
,p.id作为宠物id+
,p.name作为宠物名+
“来自客户c”+
“在p.owner\u id=c.id上左加入宠物p”+
“你的名字在哪里?”+
“凭身份证订购”;
try(PreparedStatement stmt=conn.prepareStatement(sql)){
stmt.setString(1,“%DOE%”);
try(ResultSet rs=stmt.executeQuery()){
客户=空;
while(rs.next()){
long cust_id=rs.getLong(“cust_id”);
if(customer==null | | customer.getId()!=cust_id){
客户=新客户();
customer.setId(cust_id);
customer.setName(rs.getString(“cust_name”);
customer.setDob(rs.getDate(“cust_-dob”);
客户。添加(客户);
}
long pet_id=rs.getLong(“pet_id”);
如果(宠物id!=0){
宠物=新宠物();
pet.setId(pet_id);
pet.setName(rs.getString(“pet_name”);
宠物主人(顾客);
customer.addPet(pet);
}
}
}
}
如果表Pet
的列id
是BIGSERIAL
,为什么字段id
aString
?它应该是一个长的。此外,表Pet
不应该有两列类型BIGSERIAL
。这只是为了说明的目的。实际的模式更为合理和一致。如果表Pet
的列id
是BIGSERIAL
,为什么字段id
是String
?它应该是long
。此外,表Pet
不应该有两列类型BIGSERIAL
。这只是为了说明的目的。实际的模式更加合理和一致。关于工具呢s像Sql2o吗?你用过它吗?我没有用过,但通过观察它似乎是criteria query的一个小版本。顺便说一下,我更喜欢Spring JDBC,因为它支持大多数现有数据库,依赖项注入(松耦合)由于它有未检查的异常和非常清晰的异常层次结构。您可以清楚地知道发生了什么确切的SQLException。像Sql2o这样的工具怎么样?您使用过它或类似的工具吗?我没有使用过它,但通过查看它,它似乎是标准q的一个小版本