Jak sprawdzić, czy liczba jest palindromem?
Dowolny język. Dowolny algorytm. (z wyjątkiem algorytmu przekształcania liczby w łańcuch, a następnie odwracania ciągu).
algorithm
language-agnostic
Esteban Araya
źródło
źródło
number
i cois a palindrome
będzie oznaczać w tym kontekście: a co z 13E31 (podstawa dziesięć)? 01210 (wiodące zero)? + 10-10 + 1 (pięciocyfrowy zrównoważony trójskładnik)?Odpowiedzi:
To jeden z problemów Projektu Euler . Kiedy rozwiązałem to w Haskell, zrobiłem dokładnie to, co sugerujesz, przekonwertuj liczbę na String. Sprawdzenie, czy łańcuch jest pallindromem, jest wtedy trywialne. Jeśli działa wystarczająco dobrze, to po co komplikować go? Bycie pallindromem jest raczej właściwością leksykalną niż matematyczną.
źródło
to describe an algorithm to convert an integer to a string, which of course requires you to understand modulo
- nie. Obliczeniowych w systemie numer docelowy, będąc w stanie dodać zrobi (pomyśl, jak powszechnie przekonwertować z przecinku do binarnego - używany do myślenia środki obliczeniowe binarne nie znaczy, że nie może zrobić, na przykład arytmetyka dziesiętny (a może zrobić konwersja z dwójkowego na dziesiętny bez dzielenia lub modulo 2).Dla dowolnej liczby:
Jeśli
n == rev
więcnum
jest palindromem:źródło
num
po podzieleniu (luźniejsze pisanie), musisz to zrobićnum = floor(num / 10)
.Działa tylko dla liczb całkowitych. Ze stwierdzenia problemu nie jest jasne, czy należy brać pod uwagę liczby zmiennoprzecinkowe lub zera wiodące.
źródło
Powyżej większości odpowiedzi, które mają trywialny problem, jest to, że zmienna int może się przepełnić.
Zobacz http://articles.leetcode.com/palindrome-number/
źródło
źródło
Umieść każdą pojedynczą cyfrę na stosie, a następnie zdejmij je. Jeśli tak samo do przodu i do tyłu, jest to palindrom.
źródło
Nie zauważyłem żadnych odpowiedzi, które rozwiązałyby ten problem bez dodatkowej spacji, tj. Wszystkie rozwiązania, które widziałem, używały ciągu znaków lub innej liczby całkowitej do odwrócenia liczby lub innych struktur danych.
Chociaż języki takie jak Java zawijają się przy przepełnieniu liczb całkowitych, to zachowanie jest niezdefiniowane w językach takich jak C. ( Spróbuj odwrócić 2147483647 (Integer.MAX_VALUE) w Javie ).
Obejściem może być użycie długiego lub czegoś podobnego, ale stylistycznie nie całkiem jak to podejście.
Otóż, koncepcja liczby palindromicznej polega na tym, że liczba powinna czytać to samo do przodu i do tyłu. Wspaniały. Korzystając z tych informacji, możemy porównać pierwszą cyfrę i ostatnią cyfrę. Sztuczka polega na tym, że dla pierwszej cyfry potrzebujemy kolejności numerów. Powiedzmy, 12321. Dzieląc to przez 10000 dostaniemy wiodącą 1. Końcową 1 można pobrać, biorąc mod z 10. Teraz, aby zredukować to do 232
(12321 % 10000)/10 = (2321)/10 = 232
.. A teraz 10000 musiałoby zostać zmniejszone o współczynnik 2. A teraz przejdźmy do kodu Javy ...Edytowane zgodnie z sugestią Hardika , aby objąć przypadki, w których w liczbie są zera.
źródło
W Pythonie istnieje szybki, iteracyjny sposób.
Zapobiega to również problemom z pamięcią z rekurencją (jak błąd StackOverflow w Javie)
źródło
Najszybszy sposób jaki znam:
źródło
Dla zabawy ten też działa.
źródło
Dlaczego odrzucać to rozwiązanie? Jest łatwy do wdrożenia i czytelny . Gdybyś został zapytany bez komputera, czy
2**10-23
jest to palindrom dziesiętny, z pewnością przetestowałbyś go, zapisując go w systemie dziesiętnym.Przynajmniej w Pythonie hasło „operacje na łańcuchach są wolniejsze niż arytmetyka” jest w rzeczywistości fałszywe. Porównałem algorytm arytmetyczny Sminka do prostego odwrócenia łańcuchów
int(str(i)[::-1])
. Nie było znaczącej różnicy w prędkości - zdarzyło się, że odwrócenie struny było nieznacznie szybsze.W językach kompilowanych (C / C ++) slogan może się utrzymywać, ale przy dużych liczbach istnieje ryzyko przepełnienia.
Wyniki w kilka sekund (im mniej, tym lepiej):
źródło
Odpowiedziałem na problem Eulera, używając bardzo brutalnej siły. Oczywiście, gdy dotarłem do nowego odblokowanego wątku powiązanego z forum, pojawił się znacznie inteligentniejszy algorytm. Mianowicie członek, który szedł przez uchwyt Begoner, miał na tyle nowatorskie podejście, że postanowiłem ponownie zaimplementować swoje rozwiązanie za pomocą jego algorytmu. Jego wersja była w Pythonie (używając zagnieżdżonych pętli) i ponownie zaimplementowałem ją w Clojure (używając pojedynczej pętli / recur).
Tutaj dla twojej rozrywki:
Były też odpowiedzi Common Lispa, ale były dla mnie niewdzięczne.
źródło
Oto wersja Scheme, która konstruuje funkcję, która będzie działać na dowolnej bazie. Ma kontrolę nadmiarowości: szybko zwraca fałsz, jeśli liczba jest wielokrotnością podstawy (kończy się na 0).
I nie odbudowuje całej odwróconej liczby, tylko połowę.
To wszystko, czego potrzebujemy.
źródło
Rekurencyjne rozwiązanie w Ruby, bez konwersji liczby na łańcuch.
źródło
Wersja Golang:
źródło
Zdejmij pierwszą i ostatnią cyfrę i porównaj je, aż skończą się. Może zostać cyfra lub nie, ale tak czy inaczej, jeśli wszystkie wyskakujące cyfry pasują, jest to palindrom.
źródło
Oto jeszcze jedno rozwiązanie w języku C ++ przy użyciu szablonów. To rozwiązanie będzie działać przy porównywaniu ciągów palindromowych bez rozróżniania wielkości liter.
źródło
metoda z nieco lepszym współczynnikiem stałym niż metoda @sminks:
źródło
oto wersja af #:
źródło
Liczba jest palindromiczna, jeśli jej reprezentacja łańcuchowa jest palindromiczna:
źródło
źródło
Aby sprawdzić podany numer to Palindrome lub nie (kod Java)
źródło
Wiele z zamieszczonych tutaj rozwiązań odwraca liczbę całkowitą i przechowuje ją w zmiennej, która wykorzystuje dodatkową przestrzeń, którą jest
O(n)
, ale tutaj jest rozwiązanie zeO(1)
spacją.źródło
Zawsze używam tego rozwiązania w Pythonie ze względu na jego zwartość.
źródło
Spróbuj tego:
źródło
Oto rozwiązanie wykorzystujące listy jako stosy w Pythonie:
zdejmowanie stosu bierze pod uwagę tylko prawą stronę liczby dla porównania i szybko nie udaje się zmniejszyć liczby sprawdzeń
źródło
źródło
źródło
źródło
Rekurencyjny sposób, niezbyt wydajny, po prostu zapewnia opcję
(Kod Pythona)
źródło