Number of palindrome splits

18

2

In this task you will take as input a non-negative integer \$n\$, and output the number of pairs of non-negative integers \$a,b\$ such that both are palindromes*, \$a \leq b\$, and \$a+b = n\$. For example if \$n\$ is \$22\$ then the valid pairs are

\$ \begin{array}{c|c} a & b \\ \hline 0 & 22 \\ 11 & 11 \\ \end{array} \$

So the output is \$2\$.

As another example, if \$n\$ is \$145\$ then the valid pairs are

\$ \begin{array}{c|c} a & b \\ \hline 4 & 141 \\ 44 & 101 \\ \end{array} \$

So the output is 2.

Your submission should be a program or function. Answers will be scored in bytes with fewer bytes being the goal.

Test Cases

\$ \begin{array}{c|c c|c} \mathrm{Input} & \mathrm{Output} & \mathrm{Input} & \mathrm{Output} \\ \hline 0 & 1 & 12 & 5\\ 1 & 1 & 13 & 4\\ 2 & 2 & 14 & 4\\ 3 & 2 & 15 & 3\\ 4 & 3 & 16 & 3\\ 5 & 3 & 17 & 2\\ 6 & 4 & 18 & 2\\ 7 & 4 & 19 & 1\\ 8 & 5 & 20 & 1\\ 9 & 5 & 21 & 0\\ 10 & 5 & 22 & 2\\ 11 & 5 & 23 & 1\\ \end{array} \$

OEIS A260254


* In base 10

Post Rock Garf Hunter

Posted 2020-02-02T15:37:55.267

Reputation: 55 382

1Related – Luis Mendo – 2020-02-02T17:16:01.167

7I like how this challenge was posted on a palindromic date, 02/02/2020 – James – 2020-02-02T17:56:01.537

3@DJMcMayhem Additionally the number of days since the beginning of the year (33) and the number of days to the end of the year (333) today are both palindromes. – Post Rock Garf Hunter – 2020-02-02T17:57:27.927

3

@DJMcMayhem I think you mean 20200202 or 2020-02-02 (ISO 8601) -- today is special, it is palindromic in the UK, the US, and internationally.

– Jonathan Allan – 2020-02-02T18:26:04.847

Answers

4

Jelly, 9 bytes

ŻŒḂ€ḋṚ$HĊ

A monadic Link accepting a non-negative integer which yields a non-negative integer.

Try it online!

How?

Counts all pairs without the \$a\leq b\$ restriction, halves and rounds up. Note that the halved count is only a fraction if \$\frac n 2\$ is a palindrome and in such cases we want to count this \$a=b\$ pair.

ŻŒḂ€ḋṚ$HĊ - Link: integer, n    e.g. 22
Ż         - zero-range               [0,1,2,...,9,10,11,12,...,21,22]
   €      - for each:
 ŒḂ       -   is palindrome (digits) [1,1,1,...,1,0,1,0,...0,1]
      $   - last two links as a monad:
     Ṛ    -   reverse                [1,0,...,0,1,0,1,...,1,1,1]
    ḋ     -   dot-product           3  (=1×1+1×0+...+1×0+1×1+0×1+...+0×1+1×1)
       H  - halve                   1.5
        Ċ - ceil                    2

Jonathan Allan

Posted 2020-02-02T15:37:55.267

Reputation: 67 804

3

JavaScript (ES6),  74  73 bytes

n=>(g=a=>a>n-a?0:![a,n-a].some(n=>[...n+''].reverse().join``-n)+g(-~a))``

Try it online!

Arnauld

Posted 2020-02-02T15:37:55.267

Reputation: 111 334

could you please tell me what is the last `` mean, thanks ! – chau giang – 2020-02-03T09:57:11.523

3

@chaugiang (g=a=>...)`` is equivalent to (g=a=>...)(['']) (TIO). So we have a=[''] for the first iteration, which happens to behave like a=0 would with our code and is turned into 1 for the 2nd iteration with -~a. All in all, this is one byte shorter than (g=a=>...)(0).

– Arnauld – 2020-02-03T10:23:16.223

The tagged template plus the usage of -~ is actually super clever I definitely need to incorporate them more – begolf123 – 2020-02-03T21:40:00.173

3

Python 2,  73 70  63 bytes

lambda n:sum(`n-v`+`v`==(`v`+`n-v`)[::-1]for v in range(n/2+1))

Try it online!

Note that:

(string_a == reverse(string_a)) and (string_b == reverse(string_b))

is equivalent to

reverse(string_a + string_b) == (string_b + string_a)

(where + is concatenation)

Jonathan Allan

Posted 2020-02-02T15:37:55.267

Reputation: 67 804

Are the backtits converting the integers to strings? – RGS – 2020-02-02T17:52:37.210

Yes, in Python 2 it is a shorthand for repr(...) – Jonathan Allan – 2020-02-02T17:56:58.963

very clever. Adapting it in Python 3 with f" " format strings I shaved 18 bytes ;) have a +1 – RGS – 2020-02-02T17:59:39.320

2

Prolog (SWI), 99 bytes

N-C:-aggregate_all(count,(between(0,N,A),B is N-A,B=<A,+A,+B),C).
+N:-atom_codes(N,C),reverse(C,C).

Try it online!

Ungolfed Code

After adding white space, this solution reads very similarly to the challenge specification. It simply asks for the number of pairs palindrome integers within specified bounds that sum to N.

count_splits(N,C) :- 
  aggregate_all(count,(
    between(0,N,A),
    B is N-A, B=<A,
    palindrome(A),
    palindrome(B)
  ),C).

palindrome(N) :-
  atom_codes(N,C),
  reverse(C,C).

ankh-morpork

Posted 2020-02-02T15:37:55.267

Reputation: 1 350

2

05AB1E, 10 bytes

ÝεÂQ}Â*O;î

Port of @JonathanAllan's Jelly answer, so make sure to upvote him as well!

Try it online or verify all test cases.

Explanation:

Ý        # Push a list in the range [0, (implicit) input-integer]
 ε       # Map each value to:
  Â      #  Bifurcate the value; short for Duplicate & Reverse copy
   Q     #  And check if it's equal to the value itself (1 if a palindrome; 0 if not)
 }Â      # After the map: bifurcate the entire list as well
   *     # Multiply the values at the same indices in the lists
    O    # Take the sum of that
     ;î  # And then halve and ceil it
         # (after which the result is output implicitly)

Kevin Cruijssen

Posted 2020-02-02T15:37:55.267

Reputation: 67 575

2

Perl 6, 44 bytes

{+grep {.flip eq[R,] $_},(^$_ Z($_...$_/2))}

Try it online!

Finds the number of pairs of numbers such that the reverse of the string representation is equal to the string representation of the reversed pair.

Jo King

Posted 2020-02-02T15:37:55.267

Reputation: 38 234

1

Python 3.8, 89 87 68 66 bytes

Adapting Jonathan's clever answer to Python 3 (with f format strings) and removing [] for a generator expression instead of list comprehension, we shave 21 bytes with

lambda n:sum(f"{i}{n-i}"==f"{n-i}{i}"[::-1]for i in range(n//2+1))

Try it online

My old answer:

lambda n:len([i for i in range(n//2+1)if(s:=str(i))==s[::-1]and(t:=str(n-i))==t[::-1]])

You can try it online

RGS

Posted 2020-02-02T15:37:55.267

Reputation: 5 047

1@JonathanAllan damn generator expressions ;) – RGS – 2020-02-02T18:01:32.270

1

Charcoal, 18 bytes

ILΦ⊕⊘θ⬤I⟦ι⁻θι⟧⁼λ⮌λ

Try it online! Link is to verbose version of code. The halved input has to be incremented because a needs to vary over the inclusive range from 0 to n/2. Explanation:

     θ              Input `n`
    ⊘               Halved
   ⊕                Incremented
  Φ                 Filter over implicit range
        ⟦           Begin list
         ι          Current index `a`
           θ        Input `n`
            ι       Current index `a`
          ⁻         Subtracted (i.e. `b`)
             ⟧      End list
       I            Vectorised cast to string
      ⬤             Both strings satisfy
                 λ  Current string
                ⮌   Reversed
               λ    Current string
              ⁼     Are equal
 L                  Length
I                   Cast to string for implicit print

Neil

Posted 2020-02-02T15:37:55.267

Reputation: 95 035

1

PHP, 83 86 85 73 bytes

for(;$i<=$argn/2;$i++)$k+=strrev($j=$argn-$i)==$j&&strrev($i)==$i;echo$k;

Try it online!

-13 bytes and bug fix thanks to @640KB

Guillermo Phillips

Posted 2020-02-02T15:37:55.267

Reputation: 561

1

JavaScript (Node.js),  70 69  67 bytes

-2 thanks to Arnauld (change each string cast from x+''+y to x+[y])

I don't really know much JavaScript, I based this around Arnauld's answer, any advice is very welcome!

n=>(g=a=>(v=n-a)<a?0:(v+[a]==[...a+[v]].reverse().join``)+g(-~a))``

Try it online!

Note that:

(string_a == reverse(string_a)) and (string_b == reverse(string_b))

is equivalent to

reverse(string_a + string_b) == (string_b + string_a)

(where + is concatenation)

Jonathan Allan

Posted 2020-02-02T15:37:55.267

Reputation: 67 804

67 bytes by coercing to strings in a slightly shorter way. – Arnauld – 2020-02-03T12:03:24.877

It also means that you can get rid of v like this, but that's the same byte count.

– Arnauld – 2020-02-03T12:08:42.093

Thanks @Arnauld ...it seems that there are many, many ways to --skin-- golf a cat in JS. – Jonathan Allan – 2020-02-03T13:07:11.567

1

C (gcc), 114 \$\cdots\$ 105 98 bytes

Saved 7 bytes thanks to rtpax!!!

i;m;p(n){for(i=0,m=n;i=i*10+n%10,n/=10;);n=i==m;}r;a;f(n){for(a=r=0;a<=n/2;)r+=p(a)*p(n-a++);n=r;}

Try it online!

Noodle9

Posted 2020-02-02T15:37:55.267

Reputation: 2 776

@rtpax Very nice, adding the if condition to the result is especially sweet - Thanks!:-) – Noodle9 – 2020-02-03T20:25:19.103

0

MathGolf, 14 bytes

)rmÑ_x^mÅε*Σ)½

Try it online.

Explanation:

)               # Increase the (implicit) input-integer by 1
 r              # Pop and push a list in the range [0, input+1)
  mÑ            # Check for each value whether it's a palindrome (1 if truthy; 0 if falsey)
    _           # Duplicate this list
     x          # Reverse the copy
      ^         # Zip the two together to create pairs
       m        # Map over each pair,
        Å       # using the following two commands:
         ε      #  Reduce by:
          *     #   Multiplying
           Σ    # Then take the sum of this list
            )   # Increase this sum by 1
             ½  # And integer-divide it by 2
                # (after which the entire stack joined together is output implicitly)

Kevin Cruijssen

Posted 2020-02-02T15:37:55.267

Reputation: 67 575

0

Perl 5 -p, 51 bytes

$\+=($,==reverse$,)&&$_==reverse;++$,<=--$_&&redo}{

Try it online!

Xcali

Posted 2020-02-02T15:37:55.267

Reputation: 7 671