Можно ли реализовать Luhn (хеширование номера кредитной карты) без внешних / пользовательских функций в Postgres?
Снятие последней цифры строки и ее обратное преобразование... они немного отличаются от Postgres до Oracle, но легко достижимы.
Этот фрагмент запроса находится примерно на полпути:
select translate(reverse(left('6011406981867628',-1)), '13579', '26159');
-- 6011406981867628 is a fake credit card number for test purposes.
Осталось только сложить все цифры, а затем изменить их на 10. Тем не менее, когда я пытаюсь это с:
select sum(regexp_split_to_table(translate(reverse(left('6011406981867628',-1)), '13579', '26159'), E'\\s*')::integer);
Я получаю следующую ошибку:
ERROR: set-valued function called in context that cannot accept a set
Имейте в виду, если я уберу сумму, как таковую:
select regexp_split_to_table(translate(reverse(left('6011406981867628',-1)), '13579', '26159'), E'\\s*')::integer;
Я получу это:
regexp_split_to_table
-----------------------
2
6
5
6
8
2
8
9
6
0
4
2
2
0
6
(15 rows)
Если я могу придумать сумму, то это просто check (n%10 = right('6011406981867628',1))
и я сделал.
Можно ли сделать сумму () на этих?
1 ответ
Можно ли реализовать Luhn (хеширование номера кредитной карты) без внешних / пользовательских функций в Postgres?
Да, это возможно, как описано здесь: https://wiki.postgresql.org/wiki/Luhn_algorithm
Чтобы ответить на ваш конкретный вопрос вокруг SUM
Вы даете неправильный тип аргумента. Вы можете сделать это, используя подзапрос:
# select SUM(regexp_split_to_table) from (select regexp_split_to_table(translate(reverse(left('6011406981867628',-1)), '13579', '26159'), E'\\s*')::integer) a;
sum
-----
66
(1 row)