扫一扫
分享文章到微信
扫一扫
关注官方公众号
至顶头条
作者:中国IT实验室 来源:中国IT实验室 2007年9月22日
关键字:
在本页阅读全文(共4页)
注意 float 和 double 类型的使用
首先需要注意的一点是,正如您所知,CLDC 1.0 (Connected Limited Device Configuration) 并没有出于性能的原因而提供 float 和 double 本机类型,即使 CLDC 1.1 和 CDC 都为其提供了支持。那么,如果您必须使用针对 CLDC 1.0 的 Web 服务,您该如何做呢?JSR-172 为您提供了部分答案。
为了在 CLDC 1.0 中缺省支持 xsd:float 和 xsd:double,实现必须 生成代码来将这些类型映射到 java.lang.String。为了支持为 float 和 double 提供本机支持的配置和平台(CLDC 1.1 和 CDC),存根生成器实现也必须 生成代码来将这些类型映射到适当的本机 Java 类型。(详细信息,请参阅参考资料,以获得指向 JSR-172: J2ME Web 服务规范的链接。)
我将演示一个添加两个 float 数的简单 Web 服务(清单 7)。
清单 7. 添加两个 float 数
public class TaskWs {
public TaskWs() {
}
/**
* Adding two float numbers and return their sum
* @param a First number to add,
* @param b Second number to add
* @return The sum of a and b.
*/
public float addTwo(float a, float b) {
return a + b;
}
}
}
|
所生成的 WSDL 定义中的 XML 数据类型定义如清单 8 所示。
清单 8. 与清单 7 对应的 WSDL 定义
<wsdl:types>
<schema targetNamespace="http://ws.test.ibm.com"
xmlns="http://www.w3.org/2001/XMLSchema"
xmlns:impl="http://ws.test.ibm.com" xmlns:intf="http://ws.test.ibm.com"
xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
xmlns:xsd="http://www.w3.org/2001/XMLSchema">
<element name="addTwoResponse">
<complexType>
<sequence>
<element name="addTwoReturn" type="xsd:float"/>
</sequence>
</complexType>
</element>
<element name="addTwo">
<complexType>
<sequence>
<element name="a" type="xsd:float"/>
<element name="b" type="xsd:float"/>
<element name="b" type="xsd:float"/>
</sequence>
</complexType>
</element>
</schema>
</wsdl:types>
|
对于针对 CLDC 1.0 的 Web 服务客户端,所生成的存根如清单 9 所示。
清单 9. 为 CLDC 1.0 生成的客户端存根
public interface TaskWs extends java.rmi.Remote {
public java.lang.String addTwo(java.lang.String _a, java.lang.String _b)
throws java.rmi.RemoteException, javax.xml.rpc.JAXRPCException;
}
|
所以,当调用 CLDC 1.0 中的 Web 服务时,您必须使用 addTwo() 方法提供两个 String 参数,而对于针对平台 CLDC 1.1 的 Web 服务客户端,所生成的服务接口与清单 10 中所描述的类似:
清单 10. 为 CLDC 1.1 生成的客户端存根
public interface TaskWs extends java.rmi.Remote {
public float addTwo(float _a, float _b)
throws java.rmi.RemoteException, javax.xml.rpc.JAXRPCException;
}
|
这将 xsd:float 映射到所生成的客户端存根中的 float 类型。看到 CLDC 1.0 和 CLDC 1.1 之间的不同之处了吗?
在为移动设备开发 Web 服务时,请注意 float 和 double 类型,因为 CLDC 1.0 虚拟机实现无法加载为 CLDC 1.1 生成的存根(使用到 float 和 double 的本机映射)。同时针对 CLDC 1.0 和 CLDC 1.1 的 Java 2 Platform Micro Edition (J2ME) 应用程序的开发人员应该使用到 java.lang.String 的缺省映射,以获得最好可重用性。
在处理输入和输出参数时注意可能出现的问题
JSR-172 指定了以副本的形式传送并以副本的形式创建返回值的所有参数。但是,当处理数据集合时,零数组 (返回零)和空数组 (返回其本身)需要密切关注。
我的建议是尽可能地避免使用空数组。当处理移动 Web 服务时,空数组可能是一个问题。
假定您需要返回任务对象数组。原始代码如清单 11 所示。
清单 11. 一个简单的值对象
public class SimpleTask {
/**
* The name of the task
*/
private String name;
/**
* The default constructor
*
*/
public SimpleTask() {
}
/**
* @return Returns the name of the task.
*/
public String getName() {
return name;
}
/**
* @param name
* The name to set.
*/
public void setName(String name) {
this.name = name;
}
}
|
Web 服务实现如清单 12 所示。
清单 12. 返回值对象的数组的方法
1 public SimpleTask[] getSimpleTasks(){
2 SimpleTask[] tasks = null;
3 /*
4 * Your code dealing with DB goes here
5 * ....
6 * tasks = ...
7 */
8 return tasks;
9 }
|
当生成 Web 服务存根和使用生成的存根测试 Web 服务时,本例中的每一个部分都将正常工作。但是,因为在结束一个阶段之前您需要使用 Jtest 进行完整的代码检查,所以当您对代码片段运行 Jtest 时,您将看到一条建议:“Return zero-length arrays instead of null”。在犹豫片刻之后后,您将赞同 Jtest 的建议。如果您返回零数组,该代码的客户端必须编写额外的代码来检查返回值是否为零(如清单 13 所示)。
清单13. 用于调用 Web 服务的客户端代码片段
SimpleTask[] tasks = service.getSimpleTasks();
if(tasks != null){
int length = tasks.length;
//do something here
}
|
当您将 SimpleTask[] tasks = null;(清单 12 中的第 2 行)修改为 SimpleTask[] tasks = new SimpleTasks[0]; 时,您只需将清单 13 编写为:
SimpleTask[] tasks = service.getSimpleTasks();
int length = tasks.length;
|
在修改之后,您会认为代码逻辑没有更改,并再次运行客户端来调用 Web 服务,但是现在却引发了异常。到目前为止,您已经根据 Jtest 的建议做了许多小的修补――您忘记修改了什么――这可能导致需要花额外的时间来努力找到发生错误的原因。这个过程真的漫长而乏味。
那么,问题究竟出在什么地方呢?一般来说,对于零对象数组(如 SimpleTask),返回的 SOAP 消息如清单 14 所示。
清单 14. 返回零数组时的 SOAP 消息
<soapenv:Body> <p147:getSimpleTasksResponse xmlns:p147="http://ws.test.ibm.com"> <getSimpleTasksReturn xsi:nil="true" /> </p147:getSimpleTasksResponse> </soapenv:Body> |
对于空数组(如 SimpleTask[] tasks = new SimpleTask[0]),SOAP 消息如清单 15 所示。
清单 15. 返回空数组时的 SOAP 消息
<soapenv:Body> <p147:getSimpleTasksResponse xmlns:p147="http://ws.test.ibm.com"> <getSimpleTasksReturn /> </p147:getSimpleTasksResponse> </soapenv:Body> |
其不同之处在于 <getSimpleTasksReturn/> 和 <getSimpleTasksReturn xsi:nil = true> 之间。图 2 说明了空数组参数大部分时间是无效的。对于自定义的数据类型(包括另一个自定类型的数组),不要将类变量初始化为空数组――相反,要将其初始化为零数组,尽管所生成的空数组和零数组的 WSDL 定义是相同的。
图 2. 根据 JSR-172 编码零数组参数和空数组参数
结束语
在处理移动 Web 服务时,您需要更加谨慎,因为移动 Web 服务规范只支持部分 API。如果您计划开发移动 Web 服务,则当您处理值类型和集合类型时,我向您介绍了一些窍门。此外,我还提供了以下信息:
如果您非常迫切的想了解IT领域最新产品与技术信息,那么订阅至顶网技术邮件将是您的最佳途径之一。