在开发中我们遇到日期格式转换及显示特定的日期格式是最常用的,那么国际化怎么使用呢?
首先使用<fmt>标签应先导入(国际化标签)
<%@ taglib prefix="fmt" uri="http://java.sun.com/jsp/jstl/fmt" %>
其uri可在fmt.tld文件下
1. 日期格式化
|
<fmt:formatDate value=“${XXX.date}” pattern=“yyyy-MM-dd HH:mm:ss”/>
value:要格式化的日期
pattern:日期格式化的格式
2 数字格式化
<fmt:formatNumber value="12" type="currency" pattern="$.00"/> -- $12.00 |
1.java格式化输出:
DecimalFormat df = new DecimalFormat("格式"); String fmt =df.format(double); 符号 意义 0 一个数位 # 一个数位,前导零和追尾零不显示 . 小数点分割位置 , 组分隔符的位置 - 负数前缀 % 用100乘,并显示百分号 其他任何符号 在输出字符串中包括指定符号 |
2.编程实现固定文本的国际化
<%@ page language="java" import="java.util.*" pageEncoding="gbk"%>
<%@ taglib uri="http://java.sun.com/jsp/jstl/fmt" prefix="fmt"%>
<%
String path = request.getContextPath();
String basePath = request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort()+path+"/";
%>
<fmt:setLocale value="${pageContext.request.locale}"/>
<fmt:setBundle basename="com.sz.i18NResource.msg" var="msg"/>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
<head>
<base href="<%=basePath%>">
<title><fmt:message key="jsp.login.title" bundle="${msg}"></fmt:message></title>
<meta http-equiv="pragma" content="no-cache">
<meta http-equiv="cache-control" content="no-cache">
<meta http-equiv="expires" content="0">
<meta http-equiv="keywords" content="keyword1,keyword2,keyword3">
<meta http-equiv="description" content="This is my page">
<meta http-equiv="content-type" content="text/html;charset=gbk">
<!--
<link rel="stylesheet" type="text/css" href="styles.css">
-->
</head>
<body>
<% pageContext.setAttribute("nowDate", new Date());
%>
${nowDate}<br>
<fmt:formatDate value="${nowDate}" dateStyle="full"/> <br>
<fmt:formatDate value="${nowDate}" pattern="yyyy年MM月dd日"/> <br>
<fmt:formatNumber value="1000" type="currecy" pattern="$.00" />
<fmt:message key="jsp.login.username" bundle="${msg}"/> <input type="text" name="username"/><br>
<fmt:message key="jsp.login.password" bundle="${msg}"/> <input type="text" name="password"/><br>
<input type="submit" value="<fmt:message key="jsp.login.submit" bundle="${msg}"/>"/>
</body>
</html>
配置国际化文件为:
jsp.login.title=\u7528\u6237\u767B\u5F55
jsp.login.username=\u7528\u6237\u540D
jsp.login.password=\u5BC6\u7801
jsp.login.submit=\u63D0\u4EA4
详解为下:
ResourceBundle类提供了一个静态方法getBundle,该方法用于装载资源文件,并创建ResourceBundle实例:
Locale currentLocale = Locale.getDefault();
ResourceBundle myResources =
ResourceBundle.getBundle(basename, currentLocale);
• basename为资源包基名(且必须为完整路径)。
代码如下:
<%
ResourceBundle bundler =
ResourceBundle.getBundle("com.sz.i18NResource.msg",
request.getLocale());
%>
<form>
<%=bundler.getString("username") %><input type="text" name="username" /><br/>
<%=bundler.getString("password") %><input type="text" name="password" /><br/>
<input type="submit" value="<%=bundler.getString("submit") %>" /><br/>
</form>
<!--
<fmt:setBundle basename="com.sz.i18NResource.msg"/>
-->
<fmt:bundle basename="com.sz.i18NResource.msg">
<form>
<fmt:message key="username" /><input type="text" name="username" /><br/>
<fmt:message key="password" /> <input type="text" name="password" /><br/>
<input type="submit" value="<fmt:message key="submit" />" /><br/>
</form>
</fmt:bundle>
当前时间的三种表现形式如下:<br><br>
(1):<fmt:formatDate value="<%=new Date() %>" type="date"/><br><br>
(2):<fmt:formatDate value="<%=new Date() %>" type="time"/><br><br>
(3):<fmt:formatDate value="<%=new Date() %>" type="both"/>
如何进行批量国际化:
如果实现此功能我们需要使用MessageFormat类,
//用{0}占位符替换敏感的数据。占位符对应着参数数组的索引
//具体样式:MessageFormat的API
String pattern = "At {0,time,short } on {1,date,medium}, a hurricance destroyed 99 houses and caused {2,number,currency} of damage";
Object params[] = {new Date(),new Date(),1000000};
MessageFormat mf = new MessageFormat(pattern,Locale.US);
String s = mf.format(params);//
System.out.println(s);
我们时候用{}占位符进行国际化,那么怎么实现的呢?这里MessageFormat类给我们提供了一个良好的映射关系如下:
为使用Format
类有效的模式字符串。
使用信息
这里有一些使用的例子。在真正的国际化程序中,消息格式模式和其他静态字符串将是从资源包中获得的。其他参数将在运行时动态地确定。
第一个例子使用静态方法MessageFormat.format
,其内部创建一个一次性使用的MessageFormat
:
输出:int planet = 7; String event = "a disturbance in the Force"; String result = MessageFormat.format( "At {1,time} on {1,date}, there was {2} on planet {0,number,integer}.", planet, new Date(), event);
At 12:30 PM on Jul 3, 2053, there was a disturbance in the Force on planet 7.
下面的示例创建一个MessageFormat
实例,可反复使用:
与int fileCount = 1273; String diskName = "MyDisk"; Object[] testArgs = {new Long(fileCount), diskName}; MessageFormat form = new MessageFormat( "The disk \"{1}\" contains {0} file(s)."); System.out.println(form.format(testArgs));
fileCount
不同值的输出:
The disk "MyDisk" contains 0 file(s). The disk "MyDisk" contains 1 file(s). The disk "MyDisk" contains 1,273 file(s).
对于更复杂的模式,你可以使用一个ChoiceFormat
产生单数和复数的正确形式:
与MessageFormat form = new MessageFormat("The disk \"{1}\" contains {0}."); double[] filelimits = {0,1,2}; String[] filepart = {"no files","one file","{0,number} files"}; ChoiceFormat fileform = new ChoiceFormat(filelimits, filepart); form.setFormatByArgumentIndex(0, fileform); int fileCount = 1273; String diskName = "MyDisk"; Object[] testArgs = {new Long(fileCount), diskName}; System.out.println(form.format(testArgs));
fileCount
不同值的输出:
The disk "MyDisk" contains no files. The disk "MyDisk" contains one file. The disk "MyDisk" contains 1,273 files.
你可以创建ChoiceFormat
编程,在上面的例子中,或通过使用模式。更多信息见ChoiceFormat
form.applyPattern( "There {0,choice,0#are no files|1#is one file|1<are {0,number,integer} files}.");
注:正如我们上面看到的,在一个ChoiceFormat
MessageFormat
产生的字符串被视为特殊的;出现“{”用来表示subformats,并引起递归。如果你创建一个MessageFormat
和ChoiceFormat
编程方式(而不是使用字符串模式),然后不小心产生一种递归本身的格式,这将导致无限循环。
当一个单一的参数在字符串中不止一次地被解析时,最后一个匹配将是解析的最终结果。例如,
MessageFormat mf = new MessageFormat("{0,number,#.##}, {0,number,#.#}"); Object[] objs = {new Double(3.1415)}; String result = mf.format( objs ); // result now equals "3.14, 3.1" objs = null; objs = mf.parse(result, new ParsePosition(0)); // objs now equals {new Double(3.1)}
同样,解析与使用含有相同参数的多次出现的模式MessageFormat
对象将返回的最后一场比赛。例如,
MessageFormat mf = new MessageFormat("{0}, {0}, {0}"); String forParsing = "x, y, z"; Object[] objs = mf.parse(forParsing, new ParsePosition(0)); // result now equals {new String("z")}