Oracle PL / SQL将字符串转换为INTEGER(最大值2147483648)

时间:2014-03-11 13:03:21

标签: string integer

请假设您有一个由6个字符组成的VARCHAR2字符串:

LETTER LETTER DIGIT LETTER LETTER LETTER LETTER LETTER

其中LETTER = A,B,C,.....,W,X,Y,Z 和 NUMBER = 0,1,2,3,.....,9

以前规则的最小字符串是:AA0AAA 具有先前规则的最大字符串是:ZZ9ZZZ

可能的组合数量为:

26 * 26 * 10 * 26 * 26 * 26 = 118813760

如何解码AA0AAA为1,AA0AAB为2,AA0AAC为3,.....,ZZ9ZZZ为118813760?

我在Oracle PL / SQL中编程。

提前感谢您的合作。

这是我的代码但未优化:(

SELECT   RIGA
  FROM   (SELECT   ROWNUM riga, alfa.*
            FROM   (WITH s1 AS (SELECT   'A' list1 FROM DUAL
                                UNION ALL
                                SELECT   'B' FROM DUAL
                                UNION ALL
                                SELECT   'C' FROM DUAL
                                UNION ALL
                                SELECT   'D' FROM DUAL
                                UNION ALL
                                SELECT   'E' FROM DUAL
                                UNION ALL
                                SELECT   'F' FROM DUAL
                                UNION ALL
                                SELECT   'G' FROM DUAL
                                UNION ALL
                                SELECT   'H' FROM DUAL
                                UNION ALL
                                SELECT   'I' FROM DUAL
                                UNION ALL
                                SELECT   'J' FROM DUAL
                                UNION ALL
                                SELECT   'K' FROM DUAL
                                UNION ALL
                                SELECT   'L' FROM DUAL
                                UNION ALL
                                SELECT   'M' FROM DUAL
                                UNION ALL
                                SELECT   'N' FROM DUAL
                                UNION ALL
                                SELECT   'O' FROM DUAL
                                UNION ALL
                                SELECT   'P' FROM DUAL
                                UNION ALL
                                SELECT   'Q' FROM DUAL
                                UNION ALL
                                SELECT   'R' FROM DUAL
                                UNION ALL
                                SELECT   'S' FROM DUAL
                                UNION ALL
                                SELECT   'T' FROM DUAL
                                UNION ALL
                                SELECT   'U' FROM DUAL
                                UNION ALL
                                SELECT   'V' FROM DUAL
                                UNION ALL
                                SELECT   'W' FROM DUAL
                                UNION ALL
                                SELECT   'X' FROM DUAL
                                UNION ALL
                                SELECT   'Y' FROM DUAL
                                UNION ALL
                                SELECT   'Z' FROM DUAL),
                        s2 AS (SELECT   'A' list2 FROM DUAL
                               UNION ALL
                               SELECT   'B' FROM DUAL
                               UNION ALL
                               SELECT   'C' FROM DUAL
                               UNION ALL
                               SELECT   'D' FROM DUAL
                               UNION ALL
                               SELECT   'E' FROM DUAL
                               UNION ALL
                               SELECT   'F' FROM DUAL
                               UNION ALL
                               SELECT   'G' FROM DUAL
                               UNION ALL
                               SELECT   'H' FROM DUAL
                               UNION ALL
                               SELECT   'I' FROM DUAL
                               UNION ALL
                               SELECT   'J' FROM DUAL
                               UNION ALL
                               SELECT   'K' FROM DUAL
                               UNION ALL
                               SELECT   'L' FROM DUAL
                               UNION ALL
                               SELECT   'M' FROM DUAL
                               UNION ALL
                               SELECT   'N' FROM DUAL
                               UNION ALL
                               SELECT   'O' FROM DUAL
                               UNION ALL
                               SELECT   'P' FROM DUAL
                               UNION ALL
                               SELECT   'Q' FROM DUAL
                               UNION ALL
                               SELECT   'R' FROM DUAL
                               UNION ALL
                               SELECT   'S' FROM DUAL
                               UNION ALL
                               SELECT   'T' FROM DUAL
                               UNION ALL
                               SELECT   'U' FROM DUAL
                               UNION ALL
                               SELECT   'V' FROM DUAL
                               UNION ALL
                               SELECT   'W' FROM DUAL
                               UNION ALL
                               SELECT   'X' FROM DUAL
                               UNION ALL
                               SELECT   'Y' FROM DUAL
                               UNION ALL
                               SELECT   'Z' FROM DUAL),
                        k1 AS (SELECT   '0' list3 FROM DUAL
                               UNION ALL
                               SELECT   '1' FROM DUAL
                               UNION ALL
                               SELECT   '2' FROM DUAL
                               UNION ALL
                               SELECT   '3' FROM DUAL
                               UNION ALL
                               SELECT   '4' FROM DUAL
                               UNION ALL
                               SELECT   '5' FROM DUAL
                               UNION ALL
                               SELECT   '6' FROM DUAL
                               UNION ALL
                               SELECT   '7' FROM DUAL
                               UNION ALL
                               SELECT   '8' FROM DUAL
                               UNION ALL
                               SELECT   '9' FROM DUAL),
                        s3 AS (SELECT   'A' list4 FROM DUAL
                               UNION ALL
                               SELECT   'B' FROM DUAL
                               UNION ALL
                               SELECT   'C' FROM DUAL
                               UNION ALL
                               SELECT   'D' FROM DUAL
                               UNION ALL
                               SELECT   'E' FROM DUAL
                               UNION ALL
                               SELECT   'F' FROM DUAL
                               UNION ALL
                               SELECT   'G' FROM DUAL
                               UNION ALL
                               SELECT   'H' FROM DUAL
                               UNION ALL
                               SELECT   'I' FROM DUAL
                               UNION ALL
                               SELECT   'J' FROM DUAL
                               UNION ALL
                               SELECT   'K' FROM DUAL
                               UNION ALL
                               SELECT   'L' FROM DUAL
                               UNION ALL
                               SELECT   'M' FROM DUAL
                               UNION ALL
                               SELECT   'N' FROM DUAL
                               UNION ALL
                               SELECT   'O' FROM DUAL
                               UNION ALL
                               SELECT   'P' FROM DUAL
                               UNION ALL
                               SELECT   'Q' FROM DUAL
                               UNION ALL
                               SELECT   'R' FROM DUAL
                               UNION ALL
                               SELECT   'S' FROM DUAL
                               UNION ALL
                               SELECT   'T' FROM DUAL
                               UNION ALL
                               SELECT   'U' FROM DUAL
                               UNION ALL
                               SELECT   'V' FROM DUAL
                               UNION ALL
                               SELECT   'W' FROM DUAL
                               UNION ALL
                               SELECT   'X' FROM DUAL
                               UNION ALL
                               SELECT   'Y' FROM DUAL
                               UNION ALL
                               SELECT   'Z' FROM DUAL),
                        s4 AS (SELECT   'A' list5 FROM DUAL
                               UNION ALL
                               SELECT   'B' FROM DUAL
                               UNION ALL
                               SELECT   'C' FROM DUAL
                               UNION ALL
                               SELECT   'D' FROM DUAL
                               UNION ALL
                               SELECT   'E' FROM DUAL
                               UNION ALL
                               SELECT   'F' FROM DUAL
                               UNION ALL
                               SELECT   'G' FROM DUAL
                               UNION ALL
                               SELECT   'H' FROM DUAL
                               UNION ALL
                               SELECT   'I' FROM DUAL
                               UNION ALL
                               SELECT   'J' FROM DUAL
                               UNION ALL
                               SELECT   'K' FROM DUAL
                               UNION ALL
                               SELECT   'L' FROM DUAL
                               UNION ALL
                               SELECT   'M' FROM DUAL
                               UNION ALL
                               SELECT   'N' FROM DUAL
                               UNION ALL
                               SELECT   'O' FROM DUAL
                               UNION ALL
                               SELECT   'P' FROM DUAL
                               UNION ALL
                               SELECT   'Q' FROM DUAL
                               UNION ALL
                               SELECT   'R' FROM DUAL
                               UNION ALL
                               SELECT   'S' FROM DUAL
                               UNION ALL
                               SELECT   'T' FROM DUAL
                               UNION ALL
                               SELECT   'U' FROM DUAL
                               UNION ALL
                               SELECT   'V' FROM DUAL
                               UNION ALL
                               SELECT   'W' FROM DUAL
                               UNION ALL
                               SELECT   'X' FROM DUAL
                               UNION ALL
                               SELECT   'Y' FROM DUAL
                               UNION ALL
                               SELECT   'Z' FROM DUAL),
                        s5 AS (SELECT   'A' list6 FROM DUAL
                               UNION ALL
                               SELECT   'B' FROM DUAL
                               UNION ALL
                               SELECT   'C' FROM DUAL
                               UNION ALL
                               SELECT   'D' FROM DUAL
                               UNION ALL
                               SELECT   'E' FROM DUAL
                               UNION ALL
                               SELECT   'F' FROM DUAL
                               UNION ALL
                               SELECT   'G' FROM DUAL
                               UNION ALL
                               SELECT   'H' FROM DUAL
                               UNION ALL
                               SELECT   'I' FROM DUAL
                               UNION ALL
                               SELECT   'J' FROM DUAL
                               UNION ALL
                               SELECT   'K' FROM DUAL
                               UNION ALL
                               SELECT   'L' FROM DUAL
                               UNION ALL
                               SELECT   'M' FROM DUAL
                               UNION ALL
                               SELECT   'N' FROM DUAL
                               UNION ALL
                               SELECT   'O' FROM DUAL
                               UNION ALL
                               SELECT   'P' FROM DUAL
                               UNION ALL
                               SELECT   'Q' FROM DUAL
                               UNION ALL
                               SELECT   'R' FROM DUAL
                               UNION ALL
                               SELECT   'S' FROM DUAL
                               UNION ALL
                               SELECT   'T' FROM DUAL
                               UNION ALL
                               SELECT   'U' FROM DUAL
                               UNION ALL
                               SELECT   'V' FROM DUAL
                               UNION ALL
                               SELECT   'W' FROM DUAL
                               UNION ALL
                               SELECT   'X' FROM DUAL
                               UNION ALL
                               SELECT   'Y' FROM DUAL
                               UNION ALL
                               SELECT   'Z' FROM DUAL)
                    SELECT   *
                      FROM   S1,
                             S2,
                             K1,
                             S3,
                             S4,
                             S5) alfa)
 WHERE       LIST1 = 'A'
         AND LIST2 = 'A'
         AND LIST3 = '1'
         AND LIST4 = 'A'
         AND LIST5 = 'A'
         AND LIST6 = 'A';

4 个答案:

答案 0 :(得分:2)

SQL Developer上测试,输入位于变量in_string

declare   
   in_string varchar2(20):= 'ZZ9ZZZ';

   type m IS VARRAY(6) OF INTEGER;
   weights m;
   in_char char(1);
   cnt number := 0;
   res number := 1;
BEGIN
   weights:= m(4569760, 175760, 17576, 676, 26, 1);
   while (cnt < length(in_string))
      loop
        cnt := cnt + 1;
        in_char := substr(in_string, cnt, 1);

        if cnt != 3 then
           res := res + (ASCII(in_char) - 65) * weights(cnt);
        else
           res := res + (ASCII(in_char) - 48) * weights(cnt);
        end if;

   end loop;
   DBMS_OUTPUT.PUT_LINE(res);
END;
/

给了我:118813760。

答案 1 :(得分:1)

您可以使用ascii函数将字母转换为数字。 &#39; A&#39; ascii = 65,&#39; Z&#39; = 90。 所以从结果中减去64并得到正确的值。

然后对于数字,加1(0映射到1,9映射到10)

请参阅下面的编辑,此部分不正确

将所有部分相乘,并且瞧:这是一个仅限SQL的解决方案。 比声明PL / SQL函数要快得多,因为对于每个结果,DB必须在SQL和PL / SQL上下文之间切换。

select t.string input 
,      to_number(ascii(substr(t.string,1,1))-64)
     * to_number(ascii(substr(t.string,2,1))-64)
     * (to_number(substr(t.string,3,1)) + 1)
     * to_number(ascii(substr(t.string,4,1))-64)
     * to_number(ascii(substr(t.string,5,1))-64)
     * to_number(ascii(substr(t.string,6,1))-64) as value
from (select 'AA0AAA' string from dual
      union all
      select 'ZZ9ZZZ' string from dual
      ) t;
select ascii('Z') from dual;

编辑 - 改进答案 我看到了ProblemFactory的答案。他正在做对:有一个权重因素。 即AA0ZZZ应低于ZZ0ZAA,而上述版本返回相同。 但是,在他的解决方案中,需要一个声明的PL / SQL函数,这会在执行大型数据集时导致性能损失。

以下查询将返回正确的值(感谢ProblemFactory):

select t.string input 
,    to_number(ascii(substr(t.string,1,1))-65)    * 4569760 --26*26*26*10*26
     +  to_number(ascii(substr(t.string,2,1))-65) * 175760  --26*26*26*10
     + to_number(substr(t.string,3,1))            * 17576   --26*26*26
     + to_number(ascii(substr(t.string,4,1))-65)  * 676     --26*26
     + to_number(ascii(substr(t.string,5,1))-65)  * 26
     + to_number(ascii(substr(t.string,6,1))-64) as value
from (select 'AA0AAA' string from dual
      union all
      select 'ZZ9ZZZ' string from dual
      ) t;

结果

INPUT       VALUE
------ ----------
AA0AAA          1 
ZZ9ZZZ  118813760 

答案 2 :(得分:0)

假设您的字符串格式是固定的,您可以通过编写一个更简单的pl / sql函数来解决这个问题,该函数接收单个字母并返回该字母的编号 - 例如,A = 0,Z = 25。 / p>

如果您知道该字母在字符串中的位置,您可以计算出该字母的价值,然后将其乘以适合该位置的26的幂。

答案 3 :(得分:0)

如果这是PL / SQL中的一个难题,那么aima中就有一个MixedRadixNumber java类。

当然可以从PL / SQL中调用java,如O'Reilly book中所述。