我正在尝试编写一个包装器方法,以使用方法名称和用户ID为我的日志消息添加前缀。我使用String.format来组成消息结构,但问题来自于String.format()
对varargs的解释private String logMessage(@NonNull String methodName, @NonNull String userId, @NonNull String message, Object... arguments) {
//String temp = String.format(message, arguments);
//String msg = String.format("%s:: User:%s : %s", methodName, userId, temp);<--This works
String msg = String.format("%s:: User:%s : " + message, methodName, userId, arguments);<--This prints address of arguments object
log.info(msg);
}
将上述方法称为
logMessage(methodName, userId, "Some text here: %s",
"test"));
以上电话打印
someMethod:: User:1266 : Some text here: [Ljava.lang.Object;@705a8dbc
为什么String.format打印字符串“test”的地址?
答案 0 :(得分:0)
argument
对象实际上是一个对象数组。当你在这种对象上调用toString()方法时,你通常会得到类似的东西:
[Ljava.lang.Object;@705a8dbc
实际上,[Ljava.lang.Object
是一个java字节码类型描述符,意思是“这是java.lang.Object类型的数组('[')('Ljava.lang.Object')
705a8dbc
这是数组的hashCode十六进制值。如果查看这个SO question,您可以看到,在接受的答案中,文档说hashCode()方法必须返回唯一标识符,并且通常通过将对象的内部地址转换为整数,但不是必需的
如果要获取数组中每个对象的toString()值,应使用:
Arrays.toString(argument);
这个静态方法返回一个字符串,其中包含用逗号分隔的每个对象的所有toString值,方括号之间如下:
[null, null, null, null, null] // Example with System.out.println(Arrays.toString(new Object[5]));
答案 1 :(得分:0)
我看到了问题,varargs实际上是一个数组而String.format没有扩展参数。我通过在消息之后传递方法名称和用户ID来解决这个问题:
post_save
并将方法修改为:
logMessageWithPrefix("Some text here: %s",
methodName, userId, "test")
不是理想的解决方案,因为ppl可能不会像方法所期望的那样传递methodname和userid,但会在方法上添加一些注释以防止混淆。