Палиндром Гольф
-
04-07-2019 - |
Вопрос
Цель:Любой язык.Наименьшая функция, которая вернет, является ли строка палиндромом.Вот мой в Питон:
R=lambda s:all(a==b for a,b in zip(s,reversed(s)))
50 символов.
Принятым ответом будет текущий наименьший ответ — он будет меняться по мере обнаружения меньших.Укажите язык, на котором написан ваш код.
Решение
7 символов в J: Не уверен, что это лучший способ, я немного новичок в J:)
p=:-:|.
объяснение: |. меняет вход. -: сравнивает. операнды неявные.
p 'radar'
1
p 'moose'
0
Другие советы
Вот мой; он написан на предметно-ориентированном языке, который я изобрел, он называется «палиндром».
p
Правка . Менее легкомысленная версия (i386 asm, синтаксис AT & T)
xor %eax, %eax
mov %esi, %edi
#cld not necessary, assume DF=0 as per x86 ABI
repne scasb
scan:
dec %edi
cmpsb
.byte 0x75, 6 #jnz (short) done
dec %edi
cmp %esi, %edi
.byte 0x72, -9 #jb (short) scan
inc %eax
done:
16 байт, строковый указатель идет в ESI, результат в EAX.
К сожалению, я не могу понять меньше тысячи слов ...
(LabVIEW. Да, они будут публиковать здесь почти все сообщения о бродягах;)
Haskell, 15 символов:
p=ap(==)reverse
Более читаемая версия, 16 символов:
p x=x==reverse x
Еще одна версия Python, которая немного короче (21 символ):
R=lambda s:s==s[::-1]
Опасаясь снижения голосов, большинство из них просто вызывают команду reverse , которая скрывает всю реальную логику программирования. Р>
Интересно, какой кратчайший способ сделать это вручную на каждом из этих языков?
С операторами C # и LINQ:
public bool IsPalindrome(string s)
{
return s.Reverse().SequenceEqual(s);
}
Если вы рассматриваете Reverse как мошенничество, вы можете сделать все это с уменьшением:
public bool IsPalindrome(string s)
{
return s.Aggregate(new StringBuilder(),
(sb, c) => sb.Insert(0, c),
(sb) => sb.ToString() == s);
}
Perl (27 символов):
sub p{ Perl (27 символов):
def p(a)a==a.reverse end
Рубин (24 символа):
<*>[0]eq reverse Perl (27 символов):
<*>
Рубин (24 символа):
<*>[0]}
Рубин (24 символа):
<*>73 чистых, читабельных символа, написанных на Java
boolean p(String s){return s.equals(""+new StringBuffer(s).reverse());}
мир :)
Бессмысленная версия Haskell (15 символов, хотя на самом деле не работает, если вы не включите Control.Arrow и Control.Monad и игнорируете ограничение мономорфизма):
p=ap(==)reverse
Lua больше ориентируется на удобочитаемость, чем на краткость, но при этом делает честные 37 символов:
function p(s)return s==s:reverse()end
вариант, просто для удовольствия (того же размера):
p=function(s)return s==s:reverse''end
Версия JavaScript более многословна (55 символов), потому что в ней нет функции обращения строки:
function p(s){return s==s.split('').reverse().join('')}
(equal p (reverse p))
шепелявить.18 персонажей.
ок, это частный случай.Это сработало бы, если бы оно было введено непосредственно в интерпретатор Lisp и p уже был определен.
в противном случае это было бы необходимо:
(defun g () (equal p (reverse p)))
28 символов.
Я расскажу немного подробнее: полный код на c, скомпилируйте и отправляйтесь.
90 символов
main(int n,char**v){char*b,*e;b=e=v[1];while(*++e);for(e--;*b==*e&&b++<e--;);return b>e;}
F # (очень похоже на пример C #)
let p s=let i=0;let l=s.Length;while(++i<l)if(s[i]!=[l-i-1]) 0; 1;;
PHP:
function p($s){return $s==strrev($s);} // 38 chars
или просто
$s==strrev($s); // 15 chars
Разве использование обманчивой функции на вашем языке не является обманом? Я имею в виду, глядя на решение Ruby как
def p(a)a==a.reverse end
вы можете легко переписать это как
def p(a)a==a.r end
и просто скажите, что вы сделали метод расширения в своем коде, чтобы " r " называется обратным. Мне бы хотелось, чтобы люди публиковали решения, не содержащие вызовов других функций. Конечно, функция длины строки должна быть разрешена.
Рубин без реверса - 41 символ
def m(a)a==a.split('').inject{|r,l|l+r}end
VB.Net - 173 символа
Function P(ByVal S As String) As Boolean
For i As Integer = 0 To S.Length - 1
If S(i) <> S(S.Length - i - 1) Then
Return False
End If
Next
Return True
End Function
Гольфскрипт, 5 символов
.-1%=
$ echo -n abacaba | ruby golfscript.rb palindrome.gs
1
$ echo -n deadbeef | ruby golfscript.rb palindrome.gs
0
Common Lisp, коротко-читерская версия (23 символа):
#L(equal !1(reverse !1))
#L - это макро-символ читателя, реализованный SHARPL-READER в итерационном пакете. Это в основном эквивалентно (лямбда (! 1) ...).
Common Lisp, длинная версия, использующая только примитивы (137, включая пробелы, сжимаемые до 108):
(defun p (s)
(let ((l (1- (length s))))
(iter (for i from l downto (/ l 2))
(always (equal (elt s i) (elt s (- l i)))))))
Опять же, он использует итерацию, которая в основном является более чистой версией встроенного средства LOOP, поэтому я склонен относиться к нему как к основному языку.
Не самое короткое и очень запоздалое, но я не мог не попробовать в MATLAB:
R=@(s)all(s==fliplr(s));
24 символа.
C # Без функции обратного 84 символа
int p(char[]s){int i=0,l=s.Length,t=1;while(++i<l)if(s[i]!=s[l-i-1])t&=0;return t;}
C # Без обратной функции 86 символов
int p(char[]s){int i=0;int l=s.Length;while(++i<l)if(s[i]!=s[l-i-1])return 0;return 1;}
VBScript 41 символ
function p:p=s=strreverse(s):end function
18-символьное регулярное выражение Perl
/^(.?|(.)(?1)\2)$/
52 символа в C, с оговоркой, что до половины строки будет перезаписано:
p(char*s){return!*s||!(s[strlen(s)-1]-=*s)&&p(++s);}
Без вызовов библиотеки это 64 символа:
p(char*s){char*e=s;while(*e)++e;return!*s||!(*--e-=*s)&&p(++s);}
Вдохновленный предыдущим постом, 69 символов
p(char*a){char*b=a,q=0;while(*++b);while(*a)q|=*a++!=*--b;return!q;}
РЕДАКТИРОВАТЬ: вниз на один символ
p(char*a){char*b=a,q=0;while(*++b);while(*a)q|=*a++%*--b;return!q;}
РЕДАКТИРОВАТЬ 2: 65 символов:
p(char*a){char*b=a;while(*b)b++;while(*a&&*a++==*--b);return!*a;}
Haskell, 28 символов, необходимо импортировать Control.Arrow.
p=uncurry(==).(id&&&reverse)
Простая реализация в C с использованием стандартных библиотечных функций, вдохновленная strlen в другом ответе C.
Количество символов: 57
p(char*s){char*r=strdup(s);strrev(r);return strcmp(r,s);}
Признание: я плохой парень, не освобождая г здесь. Моя нынешняя попытка быть хорошим:
p(char*s){char*r=strdup(s);s[0]=strcmp(strrev(r),s);free(r);return s[0];}
доводит его до 73 символов; Я думаю о любых способах сделать это короче.
Clojure, используя 37 символов:
user=> (defn p[s](=(seq s)(reverse(seq s))))
#'user/p
user=> (p "radar")
true
user=> (p "moose")
false
24 символа в Perl.
sub p{ 24 символа в Perl.
<*>[0]eq+reverse@_}
Крути 17Б:
p={it==it[-1..0]}
Недостатком является то, что он не работает с пустой строкой.
Если подумать, то выдача исключения для пустой строки разумна, поскольку вы не можете определить, является ли что-либо палиндромом или нет.
Без использования каких-либо библиотечных функций (поскольку вы действительно должны добавить стоимость #include
), вот версия C ++ в 96:
int p(char*a,char*b=0,char*c=0){return c?b<a||p(a+1,--b,c)&&*a==*b:b&&*b?p(a,b+1):p(a,b?b:a,b);}
Моя попытка в C (70 символов):
P(char*s){char*e=s+strlen(s)-1;while(s<e&&*s==*e)s++,e--;return s>=e;}
[Редактировать] Сейчас действительно работает
[Правка 2] Уменьшено с 74 до 70 с использованием int return по умолчанию
В ответ на некоторые комментарии: я не уверен, имеет ли значение злоупотребление препроцессором - вы можете просто определить все это в командной строке и сделать функцию одним символом.