38
\$\begingroup\$

Writing out numbers is among the Hello worlds of programming, often the numbers 1-10.

I want to write out many numbers! Many, Many numbers. But how many numbers do I have to write?

Task

Given an integer input, give a number as output that would give me the number of digits that would be in a string containing all integer numbers in the range from 0 to the input, inclusive. The negation identifier ("-") counts as a single character.

Example I/Os

Input: 8
Written out: 0,1,2,3,4,5,6,7,8
Output: 9

Input: 101
written out: 0,1,2,3....,99,100,101
Output: 196

Input: 102
written out: 0,1,2,3....,100,101,102
output: 199

Input -10
Written out: 0,-1,-2,-3,-4,-5,-6,-7,-8,-9,-10
output: 22

This is a . The lowest number of bytes wins!

\$\endgroup\$
0

59 Answers 59

1
2
2
\$\begingroup\$

Jelly, 6 bytes

r0Ṿ€FL

Try it online!

Jelly's surprisingly bad at this, mostly because it doesn't have a dedicated builtin for stringifying integers; it does have a builtin for stringifying anything, but that means we can't have it autovectorize over lists.

Explanation

r0Ṿ€FL
r0      All numbers from {the input} to 0, inclusive
   €    For each of those numbers numbers:
  Ṿ       Find its string representation
    F   Concatenate the resulting strings
     L  Take the length of the resulting string
\$\endgroup\$
4
  • \$\begingroup\$ The Length builtin doesn't work directly on integers? Preposterous! \$\endgroup\$ Commented Mar 10, 2017 at 14:39
  • \$\begingroup\$ Wait, can you use D instead of Ṿ€? \$\endgroup\$ Commented Mar 10, 2017 at 14:43
  • \$\begingroup\$ @ETHproductions: No, it doesn't deal with negative numbers correctly. \$\endgroup\$
    – user62131
    Commented Mar 10, 2017 at 14:48
  • \$\begingroup\$ Ah, got it. And I guess there's no 0-byte way to add 1 to every number if the input is negative :P \$\endgroup\$ Commented Mar 10, 2017 at 15:34
2
\$\begingroup\$

JavaScript (Node.js), 37 bytes

f=n=>n?(n+"").length+f(n>0?n-1:n+1):1

Port of my Python answer.

Try it online!

\$\endgroup\$
4
  • \$\begingroup\$ It's not only Node.js though, it should work on any platform that supports ES6. \$\endgroup\$ Commented Mar 10, 2017 at 13:24
  • \$\begingroup\$ Yeah, I just used the auto-generated TIO answer. \$\endgroup\$
    – Dennis
    Commented Mar 10, 2017 at 13:28
  • \$\begingroup\$ Oh cool, I didn't notice there was an option to do that :-) \$\endgroup\$ Commented Mar 10, 2017 at 13:33
  • \$\begingroup\$ Yep, either with the mouse or by pressing Esc, S, G. \$\endgroup\$
    – Dennis
    Commented Mar 10, 2017 at 13:40
2
\$\begingroup\$

Japt, 4 bytes

ò ¬l

Try it online!

Explanation:

ò ¬l
ò     // Creates a range from [0...Input]
  ¬   // Joins the array into a string
   l  // Returns the length
\$\endgroup\$
2
\$\begingroup\$

SQL (PostgreSQL), 76 bytes

SELECT sum(length(a::text))FROM generate_series(least(0,$1),greatest(0,$1))a

This is an SQL function.

\$\endgroup\$
1
  • \$\begingroup\$ SQL! That's a rare one \$\endgroup\$
    – tuskiomi
    Commented Mar 10, 2017 at 20:00
2
\$\begingroup\$

Java, 211 bytes

interface n{static void main(String[]a){int n=Integer.parseInt(a[0]),k=1,i;a[0]="";if(n<0)k=-1;for(i=0;i!=n+k;i+=k){a[0]+=i;if(i!=n)a[0]+=',';}System.out.print(a[0]);System.exit(a[0].replace(",","").length());}}

Takes number as first command line argument. Returns output as an error code:

Input: -10

0,-1,-2,-3,-4,-5,-6,-7,-8,-9,-10
Process finished with exit code 22

Ungolfed version with comments:

interface n {
    static void main(String[]a) {
        int n = Integer.parseInt(a[0]),                 // Input number 
        k = 1,                                          // For loop increment
        i;                                              // For loop counter
        a[0] = "";                                      // Empty string
        if(n < 0) k = -1;                               // If input number is negative loop increment is negative
        for(i=0; i != n + k; i += k) {                  // For loop
            a[0] += i;                                  // Append number to string
            if (i != n)                                 // If not the last number
                a[0] += ',';                            // Append comma
        }
        System.out.print(a[0]);                         // Output string
        System.exit(a[0].replace(",","").length());     // Return length of string without commas as error code
    }
}
\$\endgroup\$
2
\$\begingroup\$

K, 29 Bytes

I have a feeling there is a better way...

f:{#,/$((+;-)x<0).(0;!1+abs x)}

(+;-)x<0     ---> Call this A. If x is less that 0, return - otherwise return +
(0;!1+abs x) ---> Call this B. A list; (0;the numbers from 1 to the absolute value of x)
A.B          ---> Apply A to B, e.g1. (-).(0;0 1 2) ==> 0 -1 -2 e.g2 (+).(0;0 1 2) ==> 0 1 2
,/$x         ---> $tring x (x is numbers asc or desc) and flatten the list ,/
#x           ---> Finally count the flattened list

Some tests...

  f 8
9
  f 10
12
  f 101
196
  f 102
199
  f -10
22
  f -100
293
\$\endgroup\$
1
  • \$\begingroup\$ {$[x<0;a;0]+#,/$!1+a:abs x} for 27 bytes. Sums up string of 0..abs[input], if input was negative then add the abs[input] as this is the number of - you'd need to print the string. \$\endgroup\$
    – mkst
    Commented Dec 12, 2017 at 12:22
2
\$\begingroup\$

Clojure, 48 bytes

(count(apply str(range(min 0 %)(max 1(inc %)))))

(defn how-much-to-write? [n]
  ; Count the characters in the resulting string
  (count
    ; Basically "joins" the list with ""
    (apply str
      ; Creates an ascending/descending range, depending on the value of n
      (range (min 0 n) (max 1 (inc n))))))
\$\endgroup\$
2
\$\begingroup\$

Stacked, 25 bytes

:sign\0\abs|>*''join size

Try it online!

Explanation

:sign\0\abs|>*''join size    stack: (n)
:                            stack: (n n)
 sign                        stack: (n sign[n])
     \                       stack: (sign[n] n)
      0                      stack: (sign[n] n 0)
       \                     stack: (sign[n] 0 n)
        abs                  stack: (sign[n] 0 abs[n])
           |>                stack: (sign[n] range[0, abs[n]])
             *               negates the range if negative
              ''join         said range as a single string
                     size    the desired length
\$\endgroup\$
2
\$\begingroup\$

Scala 75 Bytes

(x:Int)=>{
  val? =Math.abs _
  (0 to?(x))./:("")((a,c)=>a+","+c* ?(x)/x).size-1
}

I'm not sure how I can improve it any further. The Math.abs is really really annoying. I think there is probably a better way to go about doing the negative stuff.

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

Vyxal, 4 bytes

0ṡṅL

Try it online!

Explanation:

0ṡ    # Range from 0 to n
  ṅ   # Join by nothing
   L  # Get the length of that
\$\endgroup\$
2
\$\begingroup\$

Pyt, 17 15 bytes

б⁺0⇹?ŕ⇹:ŕ;ŘǰąŁ

Try it online!

Đ                   implicit input; Đuplicate
 ±                  get sign
  ⁺                 increment
   0                push 0
    ⇹               swap top two items
     ?              if top of stack is truthy:
      ŕ⇹            ŕemove top of stack; swap top two items
        :ŕ          otherwise: ŕemove top of stack
          ;         either way:
           Ř        Řangify
            ǰ       ǰoin with no delimiters
             ą      convert to ąrray of characters
              Ł     get Łength; implicit print
\$\endgroup\$
2
+200
\$\begingroup\$

APL (Dyalog Extended),  9  6 bytes

⍴∊⍕¨…⎕

Try it online!

-3 thanks to @Adám

Explanation

⍴∊⍕¨…⎕
    …⎕  ⍝ Get the range from 0 to the input
  ⍕¨    ⍝ Convert each to string
 ∊      ⍝ Flatten the list into a single string
⍴       ⍝ And get the length of the string

Old 9-byter:

{⍴∊⍕¨0…⍵}
{       }  ⍝ Create a function:
     0…⍵   ⍝  Get the range from 0 to its argument
   ⍕¨      ⍝  Convert each to string
  ∊        ⍝  Flatten the list into a single string
 ⍴         ⍝  And get the length of the string
\$\endgroup\$
6
  • \$\begingroup\$ 6 \$\endgroup\$
    – Adám
    Commented Feb 25, 2023 at 19:08
  • \$\begingroup\$ @Adám nice! Can you just check my explanation? \$\endgroup\$
    – The Thonnu
    Commented Feb 25, 2023 at 19:22
  • \$\begingroup\$ Yes, that is correct, although I'd describe and ⍕¨ as two different steps. ⍕¨ converts each number into a string and flattens. \$\endgroup\$
    – Adám
    Commented Feb 25, 2023 at 20:35
  • \$\begingroup\$ Thanks, updated. \$\endgroup\$
    – The Thonnu
    Commented Feb 25, 2023 at 20:36
  • \$\begingroup\$ Is this your first APL answer? \$\endgroup\$
    – Adám
    Commented Feb 25, 2023 at 21:08
1
\$\begingroup\$

Javascript, 65 bytes

T=n=>{m=n>0?1:-1,o="";for(i=0;i!=n+m;i=i+m){o+=i}return o.length}

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

Swift, 72 bytes

let f={i in(min(i,0)...max(0,i)).reduce(0){$0+"\($1)".characters.count}}

The "characters.count" really kills the score.

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

Retina, 42 41 bytes

-(.+)
$*-¶$1
.+$
$*
\d|$
$%` 
(1*) 
$.1
.

Try it online!

Explanation

-(.+)
$*-¶$1

If the number is a negative, let's say -n (i.e. there is a - in the input), then replace the input with n -s, and n on the next line. In the end we just want to count the characters, and for -n as input, there will be exactly n - signs in the range.

.+$
$*

Convert the number at the end of string into unary.

\d|$
$%` 

Replace any digit character or the end of the string with all the text before it on the same line, plus a space. For a sequence of 1s, this results in  1 11 111 ... up until the original sequence. This builds the range from 0 to n, in unary.

(1*) 
$.1

Conversion back to decimal. Any series of 1s followed by a space is replaced with the number of 1s.

.

Count the matches of . and output it. . matches any single character except linefeed.

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

Pip, 13 12 bytes

#J:^0\,a|a,1

Takes input from command-line argument. Verify all test cases at Try it online!

Explanation

Some weird tricks in this one:

0\,a is the inclusive range from 0 to a.

If a is negative, we want to take the inclusive range from a to 0 instead. A naive approach would be a ternary expression with a<0, but we can do better. The problem is that something like (0,-11) is a perfectly valid Range object and is truthy, even though the range it represents contains no numbers1. We want to convert it to an empty list (falsey).

To achieve this, we apply unary ^ to split the Range into characters. This operator works itemwise, so for example giving it 0\,10 would result in the list [[0] [1] [2] [3] [4] [5] [6] [7] [8] [9] [1 0]]. Splitting into characters won't make a difference to the result, since we're going to join everything together anyway. But crucially, it forces the conversion of the Range into a List. So an input of -10 now results in the empty list [].

Now since [] is falsey, we can take the logical Or of the above with a,1 (i.e. range(a,1), not including the upper bound) and get the elements we want.

Next, we need to join them together. Unfortunately, Join has a higher precedence than Or, so we would need parentheses. But another approach is to modify Join with the compute-and-assign meta-operator : (which is like the = in += in C-like languages, but more flexible). This lowers the precedence of the operator such that parentheses aren't needed. Assigning to an rvalue is a warning, but not an error.

Finally, we take the length (#) of the resulting string, which is then autoprinted.

1 Such "backwards" ranges are used in string slicing, where the negative number means "the index 11 characters from the end."

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

C++ 102 Bytes

int f(int n){int o=0;std::string s;for(n=n<0?o=-n:n;n>=0;)s+=std::to_string(n--);return s.length()+o;}

Ungolfed

int f(int n)
{
    int o=0;
    std::string s;
    for(n=n<0?o=-n:n;n>=0;)
        s+=std::to_string(n--);
    return s.length()+o;
}

Will add explanations.

\$\endgroup\$
1
  • \$\begingroup\$ Suggest int o=n<0?(n=-n):0;std::string s;for(;n>=0;) instead of int o=0;std::string s;for(n=n<0?o=-n:n;n>=0;) \$\endgroup\$
    – ceilingcat
    Commented Mar 14, 2017 at 4:22
1
\$\begingroup\$

Pyth, 6 5 bytes

ljk}0
Uses ais523's Jelly algorithm, except that the range starts from 0.

Thanks to RK. for -1.

\$\endgroup\$
3
  • \$\begingroup\$ You could get rid of the M by just doing ljk}0 \$\endgroup\$
    – RK.
    Commented Mar 11, 2017 at 22:16
  • \$\begingroup\$ @RK. And I knew there is a shorter way than s`M! \$\endgroup\$ Commented Mar 12, 2017 at 7:39
  • \$\begingroup\$ that's the feeling, right? \$\endgroup\$
    – RK.
    Commented Mar 12, 2017 at 17:34
1
\$\begingroup\$

PHP, 38 35 bytes

<?=strlen(join(range(0,$argv[1]))); // 35 bytes
<?=strlen(join("",range(0,$argv[1]))); // 38 bytes

Useage: php file.php 8

The join is a little used alias of implode(), and php can easily join numbers together as a string. Titus commented that the glue isn't needed in join() if you want a empty string.

\$\endgroup\$
1
  • \$\begingroup\$ Save three bytes: The glue parameter for join is optional (see codegolf.stackexchange.com/a/86340/55735 and php.net/implode). \$\endgroup\$
    – Titus
    Commented Mar 13, 2017 at 12:38
1
\$\begingroup\$

Java 8, 80 bytes

Golfed:

n->{String r="";for(int i=0;i<=(n<0?-n:n);++i)r+=i;return r.length()-(n<0?n:0);}

Ungolfed:

public class HowMuchDoIHaveToWrite {

  public static void main(String[] args) {
    for (final int[] test : new int[][] { { 8, 9 }, { 101, 196 }, { 102, 199 }, { -10, 22 } }) {
      final int input = test[0];
      final int expected = test[1];
      final int actual = q(n -> {
        String r = "";
        for (int i = 0; i <= (n < 0 ? -n : n); ++i) {
          r += i;
        }
        return r.length() - (n < 0 ? n : 0);
      } , input);
      System.out.println("Input:    " + input);
      System.out.println("Expected: " + expected);
      System.out.println("Actual:   " + actual);
      System.out.println();
    }
  }

  private static int q(java.util.function.IntFunction<Integer> f, final int input) {
    return f.apply(input);
  }
}
\$\endgroup\$
1
\$\begingroup\$

J, 20 bytes

(#":i.1+|p)-(p+|p)%2
\$\endgroup\$
2
  • \$\begingroup\$ Welcome to PPCG! By default, all answers to code golf challenges must be full programs or functions. Taking input from predefined varibales is not allowed. \$\endgroup\$
    – Dennis
    Commented Mar 14, 2017 at 3:34
  • \$\begingroup\$ Sorry, I was unaware, I'll correct it as soon as I figure out a compact valid method. \$\endgroup\$
    – Bijan
    Commented Mar 14, 2017 at 12:56
1
\$\begingroup\$

CJam, 15 bytes

ri_g\z),f*:`:+,

Try it online!

Explanation:

ri_g\z),f*:`:+, e# Accepts an integer from STDIN.
ri              e# Get integer from STDIN.
  _g\           e# Store the integer's sign behind it.
     z)         e# Take the absolute value and increment it, to make an
                e# implicit range.
       ,        e# Create range [0..N].
        f*      e# Multiply every integer in the range with the sign we
                e# stored earlier, so as to include the - signs.
          :`    e# Map repr.
            :+  e# Concatenate.
              , e# Length.
\$\endgroup\$
1
\$\begingroup\$

Pascal, 146 Bytes

This is a complete program requiring a processor supporting Extended Pascal, ISO standard 10206, features. The number 20 may need to be adjusted but is sufficient for maxInt = 263 − 1.

program p(input,output);var s:string(20);i,n:integer;begin n:=0;read(i);for i in[i..0,0..i]do begin writeStr(s,i:1);n:=n+length(s)end;write(n)end.

Ungolfed:

program howMuchDoIHaveToWrite(input, output);
var
    temporaryPrint: string(20);
    i, totalLength: integer;
begin
    totalLength := 0;
    read(i);
    
    { The `[i..0, 0..i]` denotes a `set` constructor literal.
      This eliminates the issue of taking account `0` twice.
      The ranges `i..0` and `0..i` are (inside a set constructor)
      shorthand for all integral values within the intervals. }
    for i in [i..0, 0..i] do
    begin
        { The `:1` specifies the _minimum_ width.
          If omitted, a processor-defined default
          will be assumed. This could be, e. g. 20. }
        writeStr(temporaryPrint, i:1);
        totalLength := totalLength + length(temporaryPrint)
    end;
    
    write(totalLength)
end.

135 Bytes: Since n, the totalLength variable, is an integer, it is limited to values in the range −maxInt..maxInt, thus n := n + length(s) will never (without an error) exceed maxInt. We can deduplicate this information by using string(maxInt) as the temporaryPrint variable data type.

program p(input,output);var s:string(maxInt);i:integer;begin s:='';read(i);for i in[i..0,0..i]do writeStr(s,s,i:1);write(length(s))end.
\$\endgroup\$
1
\$\begingroup\$

Excel, 40 bytes

=SUM(LEN(SEQUENCE(ABS(A1))*-1^(A1<0)))+1

Input in cell A1.

\$\endgroup\$
0
\$\begingroup\$

C#, 59 76 bytes

n=>string.Concat(System.Linq.Enumerable.Range(n>0?0:n,(n<0?-n:n)+1)).Length;

Longer than I wanted it to be because of the minus and Range takes a start and a count not start and end.

\$\endgroup\$
0
0
\$\begingroup\$

GolfScript, 33 bytes

~.abs),\.{.abs/}0if:S;{S*`,}%{+}*

Try it online!

Explanation:

~.abs),\.{.abs/}0if:S;{S*`,}%{+}* # Evals STDIN.
~                                 # Eval.
 .abs),\                          # Store an absolute value inclusive range behind the original integer.
        .{.abs/}0if:S;            # Store the integer's sign in S.
                      {S*`,}%     # After applying the input's sign, get the length of the string representation of every integer in the range.
                             {+}* # Sum.
\$\endgroup\$
0
\$\begingroup\$

Python, 63 bytes

lambda n:sum(map(len,map(str,range(*[[0,n-1,-1],[n+1]][n>0]))))
\$\endgroup\$
0
\$\begingroup\$

Bean, 44 bytes

xxd-style hexdump:

00000000: 2653 4da0 6280 40a0 7852 a043 ccd0 80cc  &SM b.@ xR CÌÐ.Ì
00000010: a043 8b23 0020 8001 8b53 a062 4da0 4382   C.#. ...S bM C.
00000020: 53d0 80a0 1f20 8048 2043 253a            SÐ. . .H C%:

Equivalent JavaScript (adapted from @Dennis) (45 bytes):

(f=_=>A?(A+"").length+f(A-=Math.sign(A)):1)()

Explanation

Declares a recursive IIFE (immediately invoked function expression) f, using pre-initialized variable A with numeric input to count down and incrementally calculate the amount of characters in the range of numbers.

Try the demo here

\$\endgroup\$
0
\$\begingroup\$

Thunno 2 JL, 1 byte

Ė

Attempt This Online!

Thunno 2, 3 bytes

ĖJl

Attempt This Online!

Explanation

     # Implicit input
Ė    # Push [0..input]
 J   # Join into string
  l  # Push length
     # Implicit output
\$\endgroup\$
1
2

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

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