16
\$\begingroup\$

So we're all hopefully familiar with Spreadsheet 'A1' cell notation.

It's simply an alphanumeric representation of the positioning of said cell within a grid. The letter(s) represent the column positioning of the cell, and the number represents the row.

The 'letter' part can consist of 1 or more letters from the 26 letter English alphabet, all of which must be capital letters. These map to numbers through the use of 26-adic bijective numeration. The 'number' part can consist of any positive, non-zero integer.


The challenge, write a program that given the A1 notation of any cell as a single string, can output a string containing the column position represented as a number, followed by a space and then the row number.

Sample Input/Outputs below:

A1
>>1 1
B10
>>2 10
AC4 
>>29 4
AAC753
>>705 753
F123
>>6 123
GL93
>>194 93

This is my first challenge, hence the relative simplicity and potential poorness of the criteria.

EDIT: String must be letters followed by numbers and the winning criteria is the shortest code length (if that can be a thing)

EDIT: Related to this but does the reverse process with a different starting index. Some may argue that this fact makes the linked puzzle more interesting.

\$\endgroup\$
  • \$\begingroup\$ Can we take the input as, for example, an array containing the letters and the numbers: ["A", "1"] \$\endgroup\$ – Stephen Aug 16 '17 at 0:27
  • 1
    \$\begingroup\$ @StepHen No. It must be a single string containing both the letters and numbers. I should probably add, also, that the string MUST be in the order of letters followed by numbers. \$\endgroup\$ – dbr Aug 16 '17 at 0:28
  • 1
    \$\begingroup\$ We usually allow more flexible input and output formats, such as choosing newline instead of space as output separator \$\endgroup\$ – Luis Mendo Aug 16 '17 at 1:17
  • 3
    \$\begingroup\$ @DeanBrunt It depends on you, and of course you can enforce a strict format to make the challenge more difficult. But people usually enjoy the difficulty in the actual computations more than in the format \$\endgroup\$ – Luis Mendo Aug 16 '17 at 1:21
  • 4
    \$\begingroup\$ It's because the formatting does not add any value to the actual challenge itself \$\endgroup\$ – Adnan Aug 16 '17 at 1:22

20 Answers 20

4
\$\begingroup\$

05AB1E, 12 11 bytes

áÇ64-₂βð¹þJ

Uses the 05AB1E encoding. Try it online!

\$\endgroup\$
20
\$\begingroup\$

Microsoft Excel, 43 Bytes.

=COLUMN(INDIRECT(A1))&" "&ROW(INDIRECT(A1))

I couldn't help myself, I just had to use the right tool for the job. Takes input on A1.

Test Cases

\$\endgroup\$
11
\$\begingroup\$

Microsoft Excel, 40 bytes

Brasilian Portuguese language version.

=COL(INDIRETO(A1))&" "&LIN(INDIRETO(A1))

Translated (and therefore golfed) version of ATaco's solution.

\$\endgroup\$
  • \$\begingroup\$ I can't remember if Excel allows this like sheets, but could you use the suggestion by @Uriel on another answer and lose the last 2 parentheses? \$\endgroup\$ – dbr Aug 16 '17 at 20:48
  • \$\begingroup\$ That suggestion (omitting rightmost parentheses) throws a warning in Excel that you have to confirm to proceed, so I don't think it's allowed here. \$\endgroup\$ – pajonk Aug 17 '17 at 5:37
  • \$\begingroup\$ Ah I see. It is different to sheets then. \$\endgroup\$ – dbr Aug 17 '17 at 7:07
7
\$\begingroup\$

Python 2, 94 91 73 bytes

-3 bytes thanks to Jonathan Allan
-18 bytes thanks to tsh

s=input().strip
a=s(`3**39`);t=0
for n in a:t=t*26+ord(n)-64
print t,s(a)

Try it online!

This abuses the way that .strip works, removing all digits wtih a=s(`3**39`) where `3**39` is just a shorter way to generate the digits from 0 to 9, this will store only the chars on a that will be used to strip the chars from the numbers on s(a)

\$\endgroup\$
  • \$\begingroup\$ I don't think there is a need for strip's input to be the unique characters, so 3**39 should do the same job. \$\endgroup\$ – Jonathan Allan Aug 16 '17 at 1:30
  • 1
    \$\begingroup\$ 73 bytes \$\endgroup\$ – tsh Aug 16 '17 at 3:15
6
\$\begingroup\$

Google Sheets, 43 bytes

=COLUMN(INDIRECT(A1))&" "&ROW(INDIRECT(A1))

Try it online!

A1 is the input cell. Hopefully the above link works, I've never tried code golf with Google Sheets before.

\$\endgroup\$
  • 1
    \$\begingroup\$ @ATaco There's no reason to, as duplicate answers can coexist. \$\endgroup\$ – Conor O'Brien Aug 16 '17 at 0:47
  • 1
    \$\begingroup\$ The appearance of Google Sheets and Microsoft Excel answers pleases me. \$\endgroup\$ – dbr Aug 16 '17 at 0:56
  • 5
    \$\begingroup\$ you can do =COLUMN(INDIRECT(A1))&" "&ROW(INDIRECT(A1 for 41 bytes. sheets fills in missing right parens. \$\endgroup\$ – Uriel Aug 16 '17 at 12:34
5
\$\begingroup\$

JavaScript, 72 bytes

x=>x.replace(/\D+/,s=>[...s].reduce((n,v)=>n*26+parseInt(v,36)-9,0)+' ')
\$\endgroup\$
2
\$\begingroup\$

Proton, 113 bytes

k=>{b=(s=k.strip)('0123456789');str(sum(map((a=>26**a[1][0]*(ord(a[1][1])-64)),enumerate(b[to by-1]))))+' '+s(b)}

Try it online!

-19 bytes borrowing Rod's algorithm (note to self: add listcomps)

\$\endgroup\$
2
\$\begingroup\$

Dyalog APL, 44 bytes

(26⊥¯65+⎕AV⍳(a~⎕D)),⎕A~⍨a←⍞

Try it online!

\$\endgroup\$
  • 1
    \$\begingroup\$ Remove the parenthesis around (a~⎕D). Look-up in ⎕A instead of ⎕AV. Make tacit. Swap argument of ,. Gets down to only 16 bytes: ~∘⎕A,⍨26⊥⎕A⍳~∘⎕D \$\endgroup\$ – Adám Aug 22 '17 at 16:20
1
\$\begingroup\$

Pyth - 31 bytes

First attempt, very naive.

jd,s*V.u*26NQ1_hMxLGr-QK@`UTQZK

Try it online here.

\$\endgroup\$
1
\$\begingroup\$

Perl 5, 35 + 1 (-p) = 36 bytes

map$r=$r*26-64+ord,/\D/g;s/\D*/$r /

Try it online!

The map statement treats the column like a base26 number and converts it to decimal. The substitution replaces the letters with the numbers. The input and output are implicit in the -p flag.

\$\endgroup\$
1
\$\begingroup\$

Mathematica, 108 bytes

StringReplace[c:LetterCharacter..~~r:DigitCharacter..:>ToString@FromDigits[ToCharacterCode@c-64,26]<>" "<>r]

Operator form of StringReplace which takes the alphabetic part c of the string, converts it to a list of character codes, subtracts 64 from each code point, interprets the result as a base 26 integer, converts that integer to a String, then StringJoins a space followed by the numeric part r.

Using a regex (also 108 bytes):

StringReplace[RegularExpression["([A-Z]+)(.+)"]:>ToString@FromDigits[ToCharacterCode@"$1"-64,26]<>" "<>"$2"]
\$\endgroup\$
  • 1
    \$\begingroup\$ ToCharacterCode@c-64 can sometimes be reduced to LetterNumber@c. LetterNumber does not wrap the output in List when the input is a single character, though. \$\endgroup\$ – JungHwan Min Aug 16 '17 at 1:37
1
\$\begingroup\$

Jelly,  16  15 bytes

ØAɓi@€ḟ0ḅ26,⁸Kḟ

A full program accepting the string as an argument and printing the result

Try it online!

How?

ØAɓi@€ḟ0ḅ26,⁸Kḟ - Main link: list of characters, ref  e.g. "AAC753"
ØA              - uppercase alphabet yield               = "ABCDEFGHIJKLMNOPQRSTUVWXYZ"
  ɓ             - dyadic chain separation, call that B and place it on the right
   i@€          - first index for €ach (swap arguments)    [1,1,3,0,0,0]
      ḟ0        - filter discard zeros                     [1,1,3]
        ḅ26     - convert from base 26 to integer           705
            ⁸   - chain's left argument (ref)              "AAC753"
           ,    - pair                                     [705,['A','A','C','7','5','3']]
             K  - join with spaces                         [705,' ','A','A','C','7','5','3']
              ḟ - filter discard those in right (B)        [705,' ','7','5','3']
                - implicit print                        >>>705 753

Note: conversion from a list of numbers using the base conversion atom allows places to be outside of the expected range, so conversion from, say, [2,26,1] ("BZA") using ḅ26 is calculated as 2×262+26×261+1×260=2029 even though the "expected" representation would have been [3,0,1].

\$\endgroup\$
  • 2
    \$\begingroup\$ @Dean Brunt It is not usual to accept an answer so quickly (most leave it a week) - it may discourage others from competing. I would not be surprised to see this beaten by 05AB1E or another golfing language... \$\endgroup\$ – Jonathan Allan Aug 16 '17 at 1:34
  • \$\begingroup\$ Point taken. Still learning my way round \$\endgroup\$ – dbr Aug 16 '17 at 1:36
  • \$\begingroup\$ No problem! Welcome to PPCG, & nice first post :) \$\endgroup\$ – Jonathan Allan Aug 16 '17 at 1:37
1
\$\begingroup\$

Mathematica, 77 72 69 68 bytes

#/.{a__,b__?DigitQ}:>{f=FromDigits;f[LetterNumber@{a},26],f[b<>""]}&

Takes a list of characters.

Try it on Wolfram Sandbox

Usage

#/.{a__,b__?DigitQ}:>{f=FromDigits;f[LetterNumber@{a},26],f[b<>""]}&[{"G", "L", "9", "3"}]

{194, 93}

or

#/.{a__,b__?DigitQ}:>{f=FromDigits;f[LetterNumber@{a},26],f[b<>""]}&[Characters["GL93"]]

{194, 93}

Explanation

#/.

In the input replace...

{a__,b__?DigitQ}

A list containing two sequences a and b (with 1 or more elements), where b consists of digit characters only... (Mathematica uses lazy pattern matching, so no check is required for a)

:>

into...

f=FromDigits;

Set f to digit-to-integer conversion function.

LetterNumber@{a}

Convert a to letter numbers (a -> 1, b -> 2, etc).

{f[ ... ,26],f[b<>""]}

Convert the above from base-26 to decimal, and convert b to decimal.

\$\endgroup\$
1
\$\begingroup\$

Haskell, 67 bytes

(\(l,n)->show(foldl(\a->(a*26-64+).fromEnum)0l)++" "++n).span(>'9')

Try it online.

\$\endgroup\$
1
\$\begingroup\$

Retina, 85 bytes

[A-Z]
$& 
[T-Z]
2$&
[J-S]
1$&
T`_L`ddd
\d+
$*
{`\G1(?=.* .* )
26$*
}` (.* )
$1
1+
$.&

Try it online! Explanation:

[A-Z]
$& 

Separate the letters from each other and the final number.

[T-Z]
2$&
[J-S]
1$&
T`_L`ddd

Convert the letters to decimal.

\d+
$*

Convert everything to unary.

{`\G1(?=.* .* )
26$*
}` (.* )
$1

While there are at least three numbers, multiply the first by 26 and add it to the second.

1+
$.&

Convert everything to decimal.

\$\endgroup\$
1
\$\begingroup\$

Ruby, 50 48+1 = 51 49 bytes

Uses the -p flag. -2 bytes from m-chrzan.

sub(/\D+/){i=0;$&.bytes{|b|i=26*i+b-64};"#{i} "}

Try it online!

\$\endgroup\$
  • \$\begingroup\$ i=i*26+b-64 saves 2 bytes. \$\endgroup\$ – m-chrzan Aug 16 '17 at 15:49
1
\$\begingroup\$

><>, 42 Bytes

0i88*-:0(?\$2d**+!
$n88*+48*o\
oi:0(?;   >

Try It Online

Explanation:

0i88*-:0(?\$2d**+! Read in the Letters part of the input
0                  Push an initial 0 to the stack
 i                 Read a character of input
  88*-             Subtract 64 to get from the ascii code to its value ('A'=1,'B'=2 etc.)
      :0(?\        If the value is less than 0, break out of this loop
           $2d**   Multiply our accumulator by 26
                +  Add our new number to the accumulator
                 ! don't add a new zero to the stack

The above loop will read in the first number of the numbers part (eg. '3' in "AB34") before breaking, and will have already subtracted 64 from it, so the next bit of code has to deal with that

$n88*+48*o\        Output a space, and prepare to output the first number we read in during the previous loop
          \        Loop round to the left end of this line
$n                 Output the value of the letters part as a number
  88*+             Add the 64 we subtracted from the first number
      48*o         Output a space
          \        Enter the next loop

This loop starts by outputting a character which will either be the 1st character read in by the first loop, or the character read in by the previous iteration of this loop.

oi:0(?;   >        Output the numbers part, by just echoing it
          >        Loop round to the start of the line
o                  Output the character
 i                 Read in the next character
  :0(?;            If the value read in was less than 0, terminate
\$\endgroup\$
1
\$\begingroup\$

Ruby, 64 61 59 bytes

->s{s.sub(/\D+/){"#{$&.bytes.reduce(0){|t,b|t*26+b-64}} "}}

Saved 2 bytes thanks to Value Ink.

\$\endgroup\$
  • 1
    \$\begingroup\$ $& is the last regex match, so use it instead of m to save 2 bytes. \$\endgroup\$ – Value Ink Aug 16 '17 at 19:59
1
\$\begingroup\$

Excel-VBA Immediate window, 44 45 Bytes (36 35)

Set v=Range([A1]):?trim(v.Column &" "&v.Row);

1 byte added to suppress the trailing newline


Or for 35 with leading whitespace

Set v=Range([A1]):?v.Column""&v.Row

1 byte saved thanks to @TaylorScott!

Both take input from cell A1, output to the VBE Immediate window

\$\endgroup\$
  • 1
    \$\begingroup\$ I'm gonna go ahead and say that the leading whitespace answer is a valid response as having to remove it would force the use of Trim() on nearly all numeric answers - and on that not I would go with Set v=Range([A1]):?v.Column""&v.Row over your current solution \$\endgroup\$ – Taylor Scott Aug 20 '17 at 20:52
  • \$\begingroup\$ also, darn, I can't believe I missed this question when it came out! \$\endgroup\$ – Taylor Scott Aug 20 '17 at 20:53
  • \$\begingroup\$ @TaylorScott Oh nice trick using the "" - I guess Excel knows to insert the ; when the character following Column can't be part of the routine name. I wonder if there's a single character that could do the same thing, probably not. Yes, I would have guessed the leading space would be acceptable for most qus, but for this one I think it's more of a "Print this exact string". I did ask (last comment on question) and was told no leading space or newline. \$\endgroup\$ – Greedo Aug 21 '17 at 10:31
  • 1
    \$\begingroup\$ also, when I saw the question title, I immediately knew I should have a go if you or someone else hadn't already! As the other Excel-based answers say, right tool for the job. \$\endgroup\$ – Greedo Aug 21 '17 at 10:35
1
\$\begingroup\$

Lua, 127 Bytes

Some nice string manipulations going there, I'm using some function that are usually never used while golfing in lua :D. The best way to golf this would be to find an other way to iterate over the column part of the input while being able to retain the position of each letter. I didn't ^^'.

Try it online!

I=...l=I:gsub("%d",""):reverse()r=0
for i=1,#l
do
r=r+(l:sub(i,i):byte()-64)*math.pow(26,i-1)end
print(r.." "..I:gsub("%a",""))

Explanation

I=...                       -- shorthand for the input
l=I:gsub("%d","")           -- shorthand for the column part
   :reverse()               -- letters are put in reverse order to calculate their weight
r=0                         -- column number
for i=1,#l                  -- iterate over the letters of the input
do
  r=r+                      -- add to the column number
      (l:sub(i,i):byte()-64)-- the byte value of the current letter minus 64 (A=1 this way)
      *math.pow(26,i-1)     -- then apply its weight in base 26
end
print(r                     -- output the column number
        .." "               -- a space
        ..I:gsub("%a",""))  -- and the row number
\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.