Jump to content

Recommended Posts


I want to create or calculate a unique 8-digit ID (checksum/hash/etc) for variable-sized texts.

 

I am not sure the ID has to be a certain limited length depending on the length of the actual text, but I would like the ID to be as small as possible.  I definitely don't want a GUID. 

 

EXAMPLE: 

Name    comment
------  --------------------
car     neon.
sumvac  is not my favorite any more but i do like the cooler autom
car     neon.

RESULT: 

ID        Name    comment
--------  ------  ------------
AT1UW72Z  car     neon.
0B1UR7PY  sumvac  is not my favorite any more but i do like the cooler autom
AT1UW72Z  car     neon.

I want to add RESULT to a database table.  Duplicates are okay since I can use a query to remove them from a query/report run.  Or, I can remove them completely (at a later time) and just have unique table entries.  But in general, duplicate entries are acceptable. 

 

Is there anything already included in Delphi that supports this?  I will be working in XE7 and/or 12.2 IDE's.

 

Thanks in advanced. 

 

Share this post


Link to post
7 hours ago, JohnLM said:


I want to create or calculate a unique 8-digit ID (checksum/hash/etc) for variable-sized texts.

 

I am not sure the ID has to be a certain limited length depending on the length of the actual text, but I would like the ID to be as small as possible.  I definitely don't want a GUID. 

 

EXAMPLE: 


Name    comment
------  --------------------
car     neon.
sumvac  is not my favorite any more but i do like the cooler autom
car     neon.

RESULT: 


ID        Name    comment
--------  ------  ------------
AT1UW72Z  car     neon.
0B1UR7PY  sumvac  is not my favorite any more but i do like the cooler autom
AT1UW72Z  car     neon.

I want to add RESULT to a database table.  Duplicates are okay since I can use a query to remove them from a query/report run.  Or, I can remove them completely (at a later time) and just have unique table entries.  But in general, duplicate entries are acceptable. 

 

Is there anything already included in Delphi that supports this?  I will be working in XE7 and/or 12.2 IDE's.

 

Thanks in advanced. 

 

Look at the System.Hash unit, this kind of problem is usually the domain of hashing.

Share this post


Link to post

progress update on this endeavour. . .

 

I've been researching all about Hash and then Hash'ing a string. And I have it sort of working, but there are some issues. 

 

The way I understand it, when a hash is created it is a longword, or cardinal or other value, depending on the implementation of the function doing the hash process. 

 

So, take for instance the following: 

 

// link; https://stackoverflow.com/questions/3690608/simple-string-hashing-function
function StrHash(const st:string): cardinal;
var
 i:integer;
begin
  result:=0;
  for i:=1 to length(st) do
   result:=result*$20844 xor byte(st[i]);
end;

This function returns a Cardinal value. 

 

Then, I wrote the following to help me see what is going on and how its working for my needs. I do not need any security. It is not that level. 

 

procedure TForm1.btnGenClick(Sender: TObject);
var
  s: ansistring;
  c: cardinal;
  i: integer;
  hashLen: integer;
begin
  // c := strhash(edit1.Text); m1.Lines.Add(c.ToString()); // works; // debugging purposes 
  c := StrHash(edit1.Text);       // get/calculate the hash and store it in 'c'
  i:=c;                           // convert cardinal into integer value so i can intTostr(i)
  hashLen := length(intTostr(i)); // get the length and store it.  (But I want an even number length for the Hex output. 
                                  // which is next question, "how do I do that?") *** 
  s := inttohex(i,hashLen);       // convert the hash value, I into a string
  m1.Lines.Add(s);                // and display it--this will be the ID, the hash of the string, any length, say up to 255-chars
end;

 

With regard to the final hash ID, I would like to keep it in a specific length so that the output is clean and not croked/jaggid when I display a bunch in a report/output. 

So, I thinking that I need to calculate "even" numbers from the hashLen variable. So, if hashLen is 9 I want to add 1 and make it 10. If hashLen is 8, nothing to do. 

 

This is what I have so far, and although it does seem work, it has some problems/drawbacks. 

 

Share this post


Link to post

PS; To clarify:  The string (edit1.text) can be any length, from 1-char up to 255-char in length. But the hash value, once converted to a Hex string, I want to be as short as possible, not 255-char.  That is for the edit1.text.  I want the hash value to be around 8 to 12 chars if possible. But if not, then I want to at least "pad" with zero's. 

Share this post


Link to post
6 hours ago, JohnLM said:

I want to be as short as possible

"as short as possible" is not a usable specification. The shortest possible key is zero characters long. The longer the key, the fewer key collisions.

 

You need to specify the exact length you want your key to be.

 

Also, are you really sure that you want to hex encode the key? With hex encoding you are wasting half the bits by using 8 bits (i.e. an ansichar) to represent a 4 bit value (i.e. a hex digit).

A more efficient encoding would be something like Base32 (5 bits per byte) or Base64 (6 bits per byte). I believe Delphi has implementations of both. Search the source (or wait for someone here to write what they are, as I'm sure they will do).

Share this post


Link to post

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

×