108
\$\begingroup\$

You've just been hired by a German car manufacturing company. Your first task, as an engineer, is to write a program that computes the ecological footprint of ASCII strings.

The ecological footprint of character is computed as follows:

Write the character's ASCII code in binary, and count the number of 1's.

For example, A has a footprint of 2, but O is dirtier with a footprint of 5.

The global footprint of a string is the sum of the footprints of its characters. An empty string has a footprint of zero.

Your program must accept an ASCII string as parameter (through command line or input), compute its ecological footprint, and output it. The program itself must be ASCII encoded.

There is a hiccup though. As your company wishes to enter a new market with stricter environmental rules, you need to tune your program so that it behaves differently in "test mode". Thus:

The program should output 0 when it receives the string test as parameter.

Scoring

The source code with the smallest ecological footprint wins (and yes, the answer test is forbidden!)

\$\endgroup\$
16
  • 39
    \$\begingroup\$ I'm sorry, I haven't been keeping up with the news, but I've just read it. Can we assume the German car company is definitely NOT called Volkswagen? \$\endgroup\$ Commented Sep 25, 2015 at 11:18
  • 8
    \$\begingroup\$ For reference, most costly to less costly characters: \x7F}~_?{ow7yvu/s\x1F;=znm>k|OW[]^gc\x1Ex\x1D\eef\\'ZY+-VU.St\x173iNM5K6r\x0FG9:q<ljQ\x15\x13pC\aEF8IJL4\x0E21\x16RTh,X*)\x19\v&%\x1A#d\x1C\rab`!\"$(\x180\x05A\x14B\x12\x11DHP\x03\f\x06\n\t\x80\x10\x01@\x04\b\x02 \x00 \$\endgroup\$
    – Caridorc
    Commented Sep 25, 2015 at 11:59
  • 21
    \$\begingroup\$ @steveverrill It is a fictional company, but its name indeed starts with V and has a W somewhere in the middle. But any similarities with reality is mere coincidence, least someone sues us. \$\endgroup\$ Commented Sep 25, 2015 at 12:40
  • 18
    \$\begingroup\$ They're lying to you! 1's are much more ecologically friendly than 0's. Want proof? Print out your source code in binary. 0's use nearly twice as much ink as 1's. And if you code with a dark background, they also waste more electricity to display on your screen. (If you code with a white background, you're already wasting electrons rendering all that white, so clearly any environmentally conscious programmer should be using a black background in their editor.) To be extra eco-friendly, we should all be writing in Whitespace... \$\endgroup\$ Commented Sep 27, 2015 at 18:03
  • 2
    \$\begingroup\$ I actually have a concept for a language where the program would just be one character, but unfortunately I haven't made an interpreter yet. \$\endgroup\$
    – DanTheMan
    Commented Sep 28, 2015 at 4:13

39 Answers 39

1
2
2
\$\begingroup\$

Groovy, 326 242

B=0
P=args[0]
P.bytes.each{B+=0.bitCount(it)}print P=="test"?"0":B
\$\endgroup\$
2
\$\begingroup\$

R, 251 246 241 236

s=readline();sum(if(s!="test")as.real(rawToBits(charToRaw(s))))

Usage:

> s=readline();sum(if(s!="test")as.real(rawToBits(charToRaw(s))))
topical subject
[1] 58
> s=readline();sum(if(s!="test")as.real(rawToBits(charToRaw(s))))
test
[1] 0
> s=readline();sum(if(s!="test")as.real(rawToBits(charToRaw(s))))
s=readline();sum(if(s!="test")as.real(rawToBits(charToRaw(s))))
[1] 236

Edits: Using as.double instead of as.integer lowers by 5 points the footprint.
as.real is deprecated in the current version of R but in R < 3.0 replacing as.double by as.real lowers the footprint by 10 additional points.

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

Whispers v2, 438

> InputAll
> 2
>> ?L
>> L⊥2
>> ∑L
>> Each 3 1
>> Each 4 6
>> Each 5 7
>> ∑8
>> Output 9
> "test"
>> 1=11
> 0
>> Output 13
>> If 12 14 10

Try it online!

Unfortunately, we are sort of bound to have a high score when using Whispers for this task, as the key character is >, which has a score of 5. Aside from using " instead of ' quotes, there isn't really much room for improvement without totally rewriting the method used. Using digits which score lower (01248) rather than the higher scoring ones (35679) doesn't allow us to improve, as no high-scoring single digit is repeated (3 occurs more than once, but restructuring doesn't allow us to change the 13 to something lower scoring)

Anyway, the way the program works is fairly understandable, especially for those familiar with Whispers. Our first thing to hold in mind is that 1 is the line reference for the input string. We begin on the last line, with the ternary statement

>> If 12 14 10

The thing to remember with Whispers is that, when a line begins with two > symbols, the numbers act as line references, rather than literal values. That makes this statement equivalent to

If line(12) Then line(14) Else line(10)

Lines 11 and 12, our condition, is

> "test"
>> 1=11

Remembering that line 1 is the input string, this compares the input with the string "test" and returns that boolean.

Our program then branches. First, as it's simpler, we'll take a look at the code executed if the input is the string "test":

> 0            ; line 13
>> Output 13   ; line 14
>> If 12 14 10

If so, we call line 14, which as you can see, outputs the value on line 13, a 0. Therfore, if the input is equal to the string "test", we output a 0, then quit.

However, if the input does not equal the string, we jump up to line 10. Lines 9 and 10 are as follows:

>> ∑8
>> Output 9

So, if the input isn't in test mode, we output the sum of the result from line 8, which is the final Each statement in a series of three:

> InputAll
> 2
>> ?L
>> L⊥2
>> ∑L
>> Each 3 1
>> Each 4 6
>> Each 5 7

Our first Each statement is >> Each 3 1. This maps line 3 over each character in the input. Line 3, >> ?L, takes the currently iterated character and converts it to its ordinal value. This value is then passed to line 7, which converts it to base 2, before line 8 takes the sum of that (the number of 1s in the binary expansion). This returns an array of integers, representing the number of 1s in the binary expansion of each ordinal of each character in the input. As stated above, we then take the sum of this, before outputting it and terminating.

Fun fact:

  • The markdown of this post is functionally identical to the program
  • This post has a score of 11125
\$\endgroup\$
2
\$\begingroup\$

Excel, 274

=(1-EXACT(A1,"test"))*SUM(MID(DEC2BIN(CODE(MID(A1,SEQUENCE(,LEN(A1)),1)),8),ROW(1:8),1)*1)

Link to Spreadsheet

  • EXACT is used because string comparisons using = are not case sensitive in Excel (but they are in VBA which is weird).
  • MID(A1,SEQUENCE(,LEN(A1),1) lists all of the characters horizontally.
  • CODE(~) returns the ASCII value of each character
  • DEC2BIN(~,8) converts the ASCII values to 8-bit binary
  • MID(~,ROW(1:8),1) lists each binary digit vertically creating a 2-dimensional array of characters
  • SUM(~*1) converts the characters to number and sums them
\$\endgroup\$
1
  • \$\begingroup\$ You can start the formula with - for a score of 271: -(1-EXACT(A1,"test"))*SUM(-MID(DEC2BIN(CODE(MID(A1,SEQUENCE(,LEN(A1)),1)),8),ROW(1:8),1)) \$\endgroup\$ Commented Feb 6, 2022 at 21:19
1
\$\begingroup\$

awk, 339

{while(A++<NF){for(D=0;sprintf("%c",++D)<$A;);for(;D;D=int(D/2))B+=D%2}}$0=/^test$/?0"":B

Needs to be called with awk ' ... ' FS= so I calculated the fingerprint for the code plus FS=.

It's as always a bit longer when involving ASCII codes, because awk has no direct method of getting the code of a character. So I test for every number D starting at zero, if sprintf("%c",D) results in the character we want the ASCII code for.

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

CoffeeScript, 411 391

()->((A=prompt())!="test"&&A.split("").map((P)->P.charCodeAt().toString(2).replace /0/g,"").join("")||"").length

This can probably be improved.

Functions in CoffeeScript always return.

Thanks @Jacob Krall for reducing this 20 points.

\$\endgroup\$
1
  • \$\begingroup\$ Double quote " 00100010 is more environmentally friendly than single quote ' 00100111. \$\endgroup\$ Commented Sep 25, 2015 at 17:20
1
\$\begingroup\$

Stuck, 103

Certainly not great.. Explanation pending.

s_c"2b$o]];,":+;"test"=0u?
\$\endgroup\$
1
\$\begingroup\$

ES6, 360

alert((A=prompt())!="test"?A.replace(/./g,B=>B.charCodeAt().toString(2)).replace(/0/g,"").length:0)
\$\endgroup\$
1
\$\begingroup\$

Swift 5.9, 261

let A={$0 != "test" ?$0.reduce(0){$1.asciiValue!.nonzeroBitCount+$0}:0}
\$\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.