Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/400.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 双向字符串哈希函数_Java_String_Hashcode - Fatal编程技术网

Java 双向字符串哈希函数

Java 双向字符串哈希函数,java,string,hashcode,Java,String,Hashcode,我想得到字符串的唯一数字表示形式。我知道有很多方法可以做到这一点,我的问题是你认为哪种方法最好?我不想有负数-所以java中的hashcode()函数不是很好,尽管我可以重写它。。。但我宁愿不要,因为我不是那么自信,也不想意外地弄坏东西 我的字符串都是语义web URI。使用数字表示的原因是,当我在页面上显示URI的数据时,我需要将某些内容传递到查询字符串中,或者放入javascript中的各个字段中。URI本身太笨重,当您将URI作为URI中的值时,它看起来很糟糕 基本上,我希望有一个名为Re

我想得到字符串的唯一数字表示形式。我知道有很多方法可以做到这一点,我的问题是你认为哪种方法最好?我不想有负数-所以java中的hashcode()函数不是很好,尽管我可以重写它。。。但我宁愿不要,因为我不是那么自信,也不想意外地弄坏东西

我的字符串都是语义web URI。使用数字表示的原因是,当我在页面上显示URI的数据时,我需要将某些内容传递到查询字符串中,或者放入javascript中的各个字段中。URI本身太笨重,当您将URI作为URI中的值时,它看起来很糟糕

基本上,我希望有一个名为
Resource
的类,它将如下所示

Resource{
  int id;
  String uri;
  String value; // this is the label or human readable name

  // .... other code/getters/setters here

  public int getId(){
    return id = stringToIntFunction();
  }

  private int stringToIntFunction(String uri){
  // do magic here
  }
}
您是否可以建议一个函数在以下情况下执行此操作:

  • 它必须是双向的,也就是说,您还可以从数值恢复原始字符串
  • 不必是双向的

  • 还有其他我没有考虑的重要问题吗?

    如果你想要它是可逆的,你就有麻烦了。散列被设计为单向的

    特别是,考虑到
    int
    有32位信息,而
    char
    有16位信息,要求可逆性意味着您只能拥有零、一个或两个字符的字符串(即使是假设您乐意将“”编码为“\0\0”或类似的内容)。当然,这是假设你没有任何存储空间。如果您可以使用存储,那么只需按顺序存储数字。。。比如:

    private int stringToIntFunction(String uri) {
        Integer existingId = storage.get(uri);
        if (existingId != null) {
            return existingId.intValue();
        }
        return storage.put(uri);
    }
    
    这里
    storage.put()
    将在内部增加一个计数器,将URI存储为与该计数器值关联,然后返回它。我猜那不是你想要的

    基本上,要执行可逆加密,我会先使用标准加密库将字符串转换为二进制格式(例如,使用UTF-8)。我希望结果是一个
    字节[]

    如果不一定是可逆的,我会考虑只使用正常<代码> HASCODE()/<代码>结果的绝对值(但是映射<代码>整数.MINVALION<代码>,因为它的绝对值不能被表示为<代码> int <代码> > .< /P> < P>散列是单向的。(这也是它们有固定长度而不考虑输入大小的部分原因)。如果您需要双向编码,您可以使用Base64编码

    为什么不能有负数?URI从哪里来?它们在数据库中吗?为什么不使用数据库键ID?如果它们不在数据库中,您可以为给定一组变量/参数的用户生成它们吗?(因此查询字符串只包含foo=1&bar=2之类的内容,您可以在服务器或JavaScript端生成URL)“唯一表示法”意味着Java提供的string.hashcode将是无用的-您很快就会遇到两个URI共享相同的hashcode

    任何双向方案都将导致难以处理的字符串,除非将URI存储在数据库中并使用记录ID作为唯一标识符


    就单向性而言,MD5哈希比简单的哈希代码更独特(但决不是唯一的),但根据您的定义,可能会接近“笨拙”!

    鉴于上述所有剩余操作(哈希函数是单向的),我会选择两种可能的解决方案:

    • 使用一些加密函数来获取表示URL的长字符串(您将获得类似->param=456ab894ce897b98f的内容(根据URL的不同,可以更长和/或更短)。例如,请参阅DES加密
    • 跟踪数据库中的URL(也可以是一个简单的基于文件的数据库,如SQLite),这样就可以有效地获得uint URL等价性

    Q1:如果要从数字中恢复字符串,则可以使用:

    1a:对字符串进行加密,除非先压缩字符串,否则该字符串的大小将相同或更长。这将生成一个看起来随机的字节数组,可以显示为Base-64

    1b:数据库或地图,数字是地图/数据库中字符串的索引

    问题2:字符串不必是可恢复的

    这里可能有各种想法。您可以用十六进制或Base-64显示哈希,以避免出现负号。Base-64中唯一的非字母数字字符是“+”、“/”和“=”。对于几乎唯一的哈希,您需要加密大小的字符,MD5(128位)、SHA-1(160位)或SHA-2(256或512位)

    MD5哈希在十六进制中类似于“D131DD02C5E6EEC4693D9A069AFF95C”;哈希越大,发生冲突的可能性越小


    rossum

    谢谢Jon,我可能不得不同意你的第二个建议。但是我不确定你所说的“将Integer.MIN_值映射到某个特定的值是什么意思,因为它的绝对值不能表示为int”,不要担心回答这个问题,对于单向情况,有很多材料(等等)@Ankur:Integer.MIN_值的绝对值是2147483648。但是,一个整数可以表示的最大正数是2147483647。因此,你必须确保不要对Integer.MIN_值调用Math.abs,而是以不同的方式处理它。是的,理想情况下,我不想查找ID的全局存储。使用加密算法似乎有意义。@安克尔:但你最初的问题是URI太大了,对吧?加密对这没什么帮助。为了保存一个很长的解释(在一个很小的盒子里),我会说我一直在使用db密钥ID,但这会降低我应用程序不同部分的性能。@Ankur有没有机会通过缓存解决这个问题?基本上是Jon建议的,一个全局哈希表。是的。我想的是,1)计算一些哈希值,2)按数字顺序存储3)定期查看此表,然后添加a,B,等等,到第二、第三、第四。。。