在java中查找系统的终结性
我发现当机器是bigindian或littleindian时,checkink的算法(INTC)是在java中查找系统的终结性,java,jvm,endianness,Java,Jvm,Endianness,我发现当机器是bigindian或littleindian时,checkink的算法(INTC)是 int is_big_endian(void) { union { uint32_t i; char c[4]; } bint = {0x01020304}; return bint.c[0] == 1; } 我怎样才能在*java中找到这样的东西?*我不想使用内置libs,因为这是一个面试问题。我想在java中找到它。JVM,因此ja
int is_big_endian(void)
{
union {
uint32_t i;
char c[4];
} bint = {0x01020304};
return bint.c[0] == 1;
}
我怎样才能在*java中找到这样的东西?*我不想使用内置libs,因为这是一个面试问题。我想在java中找到它。JVM,因此java,严格地说是big-endian,而不管主机平台如何 然而,在关联字符编码中,可以提取关于系统默认编码的信息,该编码可能具有尾端性(事实上,它可能具有尾端性) 以下是一些代码:
boolean is_big_endian()
{
return true;
}
编辑:
请参阅以下参考答案:
公平地说,调用本机代码是可能的,在那里您可以得到本机字节顺序的东西。我对此不负责,但是您可以尝试:
import java.nio.ByteOrder;
if (ByteOrder.nativeOrder().equals(ByteOrder.BIG_ENDIAN)) {
System.out.println("Big-endian");
} else {
System.out.println("Little-endian");
}
如何在java中找到这样的东西?*我不想使用内置的libs,因为这是一个面试问题。我想在java中找到它
在纯Java中,如果不调用库,就无法做到这一点。这是因为,
- Java说,如果可以避免,就不应该关心这些事情
- 作为一种语言,Java的功能相对较差,它依赖于它的库来做很多事情,而这些事情可能是另一种语言的语言功能
- 大多数人不区分语言的功能和内置库,因为这种区别很少有用
- 字节码/虚拟机本身不是big-endian或little-endian,只有真正的实现才是。;)李>
公共静态void getEndian(){
int a=0;
//0x0…01
int b=1;
//0x0..0,0.01,0..0,0..0
int combine=(b在具有sun.misc.Unsafe类并在名为“theUnsafe”的静态实例变量中存储不安全单例的JVM上,可以使用以下方法。我在Oracle JVM和openjdk上成功地测试了这一点。代码通过向内存写入一个短(2字节)值1,然后读取第一个字节来工作
import java.lang.reflect.Field;
import sun.misc.Unsafe;
public class Endianness {
private static Unsafe getUnsafe() {
Unsafe unsafe = null;
try {
Field f = sun.misc.Unsafe.class.getDeclaredField("theUnsafe");
f.setAccessible(true);
unsafe = (Unsafe) f.get(null);
} catch (Exception e) {}
return unsafe;
}
public static void main(String[] args) {
Unsafe unsafe = getUnsafe();
long address = unsafe.allocateMemory(2);
short number = 1;
unsafe.putShort(address, number);
if (unsafe.getByte(address) == 0)
System.out.println("Big Endian");
else
System.out.println("Little Endian");
unsafe.freeMemory(address);
}
}
据我所知,Java是严格意义上的big-endian。没有办法(事实上也没有理由)在不调用本机代码的情况下找出底层体系结构的终结性。我认为你运气不好。JVM会屏蔽你,使你免受这些特定于实现的细节的影响。吹毛求疵:这种使用union
是否会触发未定义的行为?我会使用char const*
替换为uint32\u t
。好的。同意java这样做不允许你找到机器的endianess。但是我如何才能用java代码找到jvm本身的endianess呢?这只是为了采访的目的。我想知道这一点的唯一原因是创建二进制文件供非java应用程序使用,或者用java构建编译器。这一点相当模糊。同意。但这是一个采访stion@user93796:那又怎样?这会神奇地使JVM的工作方式无效吗?不会。我必须想出一个算法来检测JVM是大还是小。不会MAGIC@PeterClark真的吗?如果是这样的话,那么它就不符合编写此答案时的JVM规范。@Marcin我对代码进行了更深入的研究,发现我正在使用的代码调用了native(c/c++)代码(bitmap.copyPixelsToBuffer
)以执行内存的实际复制。这可能是我返回的缓冲区是little endian的原因(它肯定是,它是一个每个颜色通道有1字节的图像,我得到的是BGRA而不是ARGB)。我不能100%确定JVM本身是否使用little endian,我可能猜不出JVM规范是否明确说明了这一点。ByteOrder.nativeOrder()上的文档提到常量存在,因为性能敏感的代码可以在本机运行。@user93796,这是一个“系统”库,它不是第三方库,IMO,公平的游戏。这以最简单的方式解决了问题-你需要一个乱七八糟的东西做什么?它不是库,它是一个内置类。没有它们,你在Java中不会走得很远。事实上,没有它们,你不会有任何进展。如果他们不喜欢你的答案,问问自己:我真的想要f吗还是一家问了这么愚蠢问题的公司?@user93796,谁说的?如果有人给我设置了一个测试,而问题的关键不是实现排序算法,我会使用现有的实现。在我看来,任何其他方法都是愚蠢的。你会雇用自己编写(可能有缺陷)排序()的人吗方法,而不是使用经过测试、理解良好的内置方法。事实上,我强烈怀疑是否有其他方法可以做到这一点。Java被设计为独立于平台,所以它的几乎所有方法都会在大端或小端机器上给你相同的结果。目前为止最好的答案是,伙计,指出为什么你会这样做不应该这样做。即使你不应该这样做,你仍然需要证明你可以这样做。我会说,看看它是如何完成的,这应该是一个合理的答案。最近我不得不创建一个自定义的替罪羊树状图,它使用int
作为键和该键的多个值,并回收其所有节点。当然,我复制了代码的好部分om TreeMap并尽可能保持名称不变。这个问题不是问你为什么不想这样做,我已经问过了
import java.lang.reflect.Field;
import sun.misc.Unsafe;
public class Endianness {
private static Unsafe getUnsafe() {
Unsafe unsafe = null;
try {
Field f = sun.misc.Unsafe.class.getDeclaredField("theUnsafe");
f.setAccessible(true);
unsafe = (Unsafe) f.get(null);
} catch (Exception e) {}
return unsafe;
}
public static void main(String[] args) {
Unsafe unsafe = getUnsafe();
long address = unsafe.allocateMemory(2);
short number = 1;
unsafe.putShort(address, number);
if (unsafe.getByte(address) == 0)
System.out.println("Big Endian");
else
System.out.println("Little Endian");
unsafe.freeMemory(address);
}
}
System.out.println(ByteOrder.nativeOrder());