java String 内存地址问题?如何获取 String 内存地址!

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了java String 内存地址问题?如何获取 String 内存地址!相关的知识,希望对你有一定的参考价值。

跪求!
求正解!
String str="hello word!";
System.out.println(str.getClass()+"@"+str.hashCode());
如此获得了str在java虚拟机中的内存地址。可这不是我想要的。
这样虚拟机最终会在堆创建另外一个实质性的内存地址!
请问那个地址如何获取?

hashCode()返回的是JVM中地址的哈希码,而不是JVM中的地址,要想得到str在物理内存中的真实地存,那只有用JNI技术调用c/c++去实现,否则无能为力,因为java超不出JVM,而JVM对物理内存地址是“不可见”的,否则java中不就有了指针,而去直接操作内存了,当然这是与java语言相违背的。这些只是我个人见解,说不定还真有高手直接用java语言得到了物理内存中的地址了呢。 参考技术A str.hashCode()不是str的jvm地址,String类的hashCode函数被重写了。 参考技术B jvm路过。。这就是正解了! 参考技术C 这个是不可以的,String重写了Hashcode(),获取的并不是物理地址
/**
* Returns a hash code for this string. The hash code for a
* <code>String</code> object is computed as
* <blockquote><pre>
* s[0]*31^(n-1) + s[1]*31^(n-2) + ... + s[n-1]
* </pre></blockquote>
* using <code>int</code> arithmetic, where <code>s[i]</code> is the
* <i>i</i>th character of the string, <code>n</code> is the length of
* the string, and <code>^</code> indicates exponentiation.
* (The hash value of the empty string is zero.)
*
* @return a hash code value for this object.
*/
public int hashCode()
int h = hash;
if (h == 0 && value.length > 0)
char val[] = value;

for (int i = 0; i < value.length; i++)
h = 31 * h + val[i];

hash = h;

return h;

在c/c++中获取java对象的内存地址

【中文标题】在c/c++中获取java对象的内存地址【英文标题】:get memory address of java object in c/c++ 【发布时间】:2017-11-13 09:36:25 【问题描述】:

假设我有一个 java 类

class NativeInterface
    public static native void access(Object obj);

而我要做的就是访问该对象的第二个字节(例如)。

即我想做这样的事情:

#include<jni.h>
#include "NativeInterface.h"
#include <stdio.h>

using byte = unsigned char;

/*
* Class:     NativeInterface
* Method:    access
* Signature: (Ljava/lang/Object)V
*/
JNIEXPORT void JNICALL Java_NativeInterface_access(JNIEnv* env, jclass _obsolete, jobject obj)
    byte byte_array[] = obj;
    printf("%c",byte_array[2]);

现在显然,这行不通。 obj 甚至可能不是 java 对象。 (jobject 定义在 jni.h 中,我还没有弄清楚它的作用。)

那么我该怎么做呢?

(尝试这种幼稚的尝试将导致

error: initializer fails to determine size of ‘byte_array’
     byte byte_array[] = obj;
                         ^~~~

,顺便说一句。)

【问题讨论】:

你不能分配给一个数组,也不能用不同于数组初始化器的东西来初始化它!请查阅您的文档,jobject 到底是什么char *objbytes = obj 之类的东西可能会起作用。 【参考方案1】:

obj 甚至可能不是 java 对象”

你几乎自己想通了。它只是比那强一点。 Java有垃圾收集。仅出于这个原因,您就知道obj 不是 java 对象,而只是一个句柄,它在垃圾收集器在内存中随机播放时引用该对象。

您现在看到了问题中的根本缺陷:“获取 java 对象的内存地址”假定您获得了有用的值。但即使你能得到一个地址,从你得到它的第一个时钟滴答开始,它也是不可靠的。

【讨论】:

我同意它不是 java 对象,我不同意如果我能得到一个地址,那将是“从第一个时钟开始就不可靠”。请参阅我的后续问题:***.com/questions/47267806/… @User1291:您正在查看幕后 JNI 代码,该代码可防止对象在 JNI 分配 Int 时移动。 我不明白你的意思。如果你是正确的,那么不安全的实现如何在执行时不做任何事情来“防止对象移动”? @User1291:这是另一个不正确的假设。 JNI 是 JVM 的组成部分,它确实可以防止对象移动。这并不奇怪,JVM 必须阻止对象移动,无论谁在对象上调用方法。 谢谢。我试图最终在 RTM 事务中执行它是否重要(请参阅***.com/questions/47220275/how-to-use-unsafe-in-jni)?我不完全确定,但我假设在获取地址的过程中读取的至少一个值将不得不在移动中改变,s.t.事务中止并且可以重试。因此,如果我们在同一事务中以事务方式解析地址并访问/修改位置……那应该可行吗?

以上是关于java String 内存地址问题?如何获取 String 内存地址!的主要内容,如果未能解决你的问题,请参考以下文章

Java String详解

如何获取到JAVA对象所在的内存地址

java中怎么输出String的地址?如何复制一个String,然后用不同的地址保存呢?

java获取浏览器地址栏地址

(JNI) 使用 GetMethodID 获取 Java 方法的内存地址

在delphi中如何获取字符串的内存地址