Meta Golf Challenge

22

5

On that challenge you have to solve that challenge.

Contest is over! Check the end of the question

Specs:

  1. Write the smallest code (Any language*).
  2. The score of an answer is the sum of:
    • Code length without whitespace.
    • Number of answers using that same language squared.
    • Length of the name of the biggest language on the contest minus the length of your language.
    • Downvotes minus Upvotes (a.k.a. minus Total of Votes)
  3. Write the position of the users and the score.
  4. Each user can write only one answer.
  5. The lowest score wins.

Testing:

So, at the end of the contest, a possible input could be (STDIN):

The columns are: Username, Language, Code length(w/o whitespace) and TotalVotes

UserA Python 100 1
UserB Perl 30 2
UserC Java 500 3
UserD Brainfuck 499 4
UserE Perl 29 5

If your user name has spaces like "My User Name" it'll become "MyUserName" so the input will always have exactly 4 columns.

The output will be (STDOUT):

1 UserE 33
2 UserB 37
3 UserA 103
4 UserD 496
5 UserC 503

Explanation:

User  P  N^2  L   V
 A   100  1   3  -1
 B    30  4   5  -2
 C   500  1   5  -3
 D   499  1   0  -4
 E    29  4   5  -5

Brainfuck is the largest name with 9 chars (9 - 9 = 0).

Perl and Java have 4 chars (9 - 4 = 5).

Python has 6 chars (9 - 6 = 3).

Perl has 2 entries so each get 4 extra points.


About languages:

The name of the language must contain only English letters (i.e. [A-Za-z]) and those which don't fit that must be "translated" to something else.

By the end of the contest, every language must have it's representation (You may propose better representations)

Examples:

Python3      -> Python
Ruby1.9      -> Ruby
Shell Script -> Shell
C++          -> Cpp
C#           -> CSharp
><>          -> Fish

Deadline: August 20, 2011 00:00 UTC

At the end of the contest, the winner must use his/her program to find the winner. It's allowed to non winners to use their programs to find the winner and tell him/her to use his/her program to find the winner. :)

The winner (see above) gets the answer accepted!

*The Whitespace language has the unfair advantage of being able to introduce unlimited complexity without a penalty on the character count. Answers written in Whitespace may be on the contest but can't win.

If you can make the logic of your program in whitespaces, you also can't win. That's a subjective topic, but if your program can increase considerably in size without being penalized, it falls in that condition.


Final Input

Alphabetical order of names (as of Aug 20th 2011 UTC 00:00)

boothby Sage 41 9
Harpyon Python 203 4
JBernardo Python 184 7
JoeyAdams PostgreSQL 225 6
jpjacobs AWK 269 4
Lowjacker Ruby 146 2
PeterTaylor Golfscript 82 4
rmackenzie CommonLisp 542 2
shesek Javascript 243 3
userunknown Scala 252 1

As both mine and boothby's answers are not allowed to win, the winner should proclaim himself the winner by editing this question and posting the final output below.

Final Output

1 boothby 39
2 PeterTaylor 79
3 Lowjacker 151
4 JBernardo 185
5 Harpyon 207
6 JoeyAdams 220
7 shesek 241
8 userunknown 257
9 jpjacobs 273
10 rmackenzie 541

JBernardo

Posted 2011-07-18T04:55:41.140

Reputation: 1 659

Is the goal to have the lowest score or the highest score? – Joey Adams – 2011-07-18T05:35:31.910

@Joey Lowest (it's code golf! :) I Fixed the question. – JBernardo – 2011-07-18T05:38:25.437

This contest favors languages with longer names, correct? – Joey Adams – 2011-07-18T06:12:43.577

Yes. It also favors languages with lots of whitespaces, answers with lots of upvotes and obscure languages. – JBernardo – 2011-07-18T06:16:26.057

8

Does that mean a solution in Whitespace will automatically win?

– Joey Adams – 2011-07-18T06:35:13.767

@Joey I thought of that, but i don't know if whitespace should be banned or not. Maybe if someone is crazy enough to write in Whitespace and don't get too much downvots he should win... – JBernardo – 2011-07-18T06:43:53.870

1Where does the information about other answers come from? Are our programs supposed to connect to StackExchange and mine the answers to this question? – Justin Morgan – 2011-07-18T16:46:57.983

It's ><>, not <><. Imagine I'd call you odranreBJ instead of JBernardo! :P (Creator of ><> here) – None – 2011-07-18T21:35:11.907

1@Justin At the end of the contest, I'll make the real program input with the answers. I gave the format – JBernardo – 2011-07-18T21:55:53.153

1@Harpyon <>< ti dexif I !sknahT – JBernardo – 2011-07-18T21:58:41.610

The input format might deserve a bit more detail. For example, some user names have spaces, which is tricky with the current example. Which might or might not be what you want, you tell us. – J B – 2011-07-18T22:10:31.717

@JB The spaces will be stripped (Like I did with your user name). Is anything else about the input format missing? – JBernardo – 2011-07-18T22:17:18.207

1Must we sort the output by scores? If so, what should we do in case of tie? – boothby – 2011-07-19T00:13:02.173

@boothby The answer posted first should win but you don't have worry about that. Just sort those with same number of points the way you like. – JBernardo – 2011-07-19T00:27:08.100

It seems there could be some evil strategies that could go on. For example, if a Javascript solution was currently winning, I could post three more solutions in Javascript to lower its score. – Peter Olson – 2011-07-21T05:37:47.190

@Peter, only one per user. I mean... you could make puppets... but don't. – boothby – 2011-07-21T06:08:10.737

@Franklin It will be on the contest but I won't choose as right answer if it wins (As said on the last paragraph). In addition, I won't choose my answer if it wins. – JBernardo – 2011-07-25T03:10:19.483

@JBernardo Yeah... I figured you'd update the rule once I posted my solution. What I didn't expect is to have a positive vote total. – boothby – 2011-07-26T20:38:13.270

Added a small bounty to remind people of the August 20 deadline. – Joey Adams – 2011-08-16T12:36:35.060

@Joey Adams Oh, nice! – JBernardo – 2011-08-16T12:39:49.223

"Perl has 2 entries so each get 4 extra points." <- they get 3 extra points, since the others get 1 point. – oenone – 2011-08-17T08:00:45.817

It would be a spec violation for my bootstrapping code to have the usage ./btstrp ./test-file as opposed to cat ./test-file | ./btstrp, correct? – arrdem – 2011-08-18T19:07:31.237

I don't get it, what are we building? A whitespace interpreter or a parsing lib for the four column input? – Xeoncross – 2011-08-18T20:07:45.977

@Xeoncross just sort the input using the rules (and they say Whitespace languages will make your answer 'invalid') – JBernardo – 2011-08-18T21:48:30.147

@rmackenzie if your language can't use stdin it might be ok... But doesn't seems like your case. – JBernardo – 2011-08-18T21:52:12.047

@Joey - May I please have a Mod ruling on the spec-compliance and legality of my posted solution? – arrdem – 2011-08-20T03:35:54.487

1@rmckenzie: I'm not a Mod. However, the problem with your wget solution is that you can arbitrarily increase the complexity of your solution without a corresponding increase in code size (the same problem with the Sage solution). Furthermore, downloading code and immediately executing it is dangerous, if it is not sandboxed properly. For these reasons, I will not put a bounty on your wget solution. – Joey Adams – 2011-08-20T03:48:53.827

@joey - my bad. Valid comments, thank you. Btw - who are the mods (if we have any)? I was under the impression that you and Peter were admins of only due to seniority. – arrdem – 2011-08-20T03:57:43.313

I awarded the bounty to Peter Taylor's Golfscript solution. He would have needed -69 votes to fall to third place. jpjacobs and rmckenzie, I am sorry to say that you have fallen below the yellow line and will be up for elimination tonight.

– Joey Adams – 2011-08-20T04:09:27.210

@mckenzie, the most visible codegolf.se mods are gnibbler, Chris Jester-Young, dmckee; there are a few more, but I don't know a better way to get a full list than to go through the entire Users page looking for blue diamonds. However, for rulings on this question the final arbiter would be JBernardo, and for rulings on the awarding of the bounty it would be Joey Adams. – Peter Taylor – 2011-08-20T05:57:33.367

Answers

11

Golfscript, 83 chars (82 not counting whitespace)

n/{},{' ':s/}%.{1=}%\{~~\~\-\.`{=}+4$\,,.*\,-+2${,}%$)\;+[\]}%$\;.,,]zip{~)s@~s@n}%

Explanation:

# Split the string containing all the input on newlines
n/
# Remove empty lines
{},
# Split each line on spaces (storing the space character in variable s)
{' ':s/}%
# We now have an array of arrays of words. Duplicate it, filter the copy to contain
# only the second word of each array, and reorder with the array of second words first
.{1=}%\
# Map each line
{
    # Unpack the array ["user" "lang" "length" "votes"] and evaluate the integers
    ~~\~\
    # Subtract votes from length and bring "lang" to the top
    -\
    # Create a function to match the string "lang"
    .`{=}+
    # Stack is currently [array of langs] "user" (length-votes) "lang" {"lang"=}
    # Duplicate the array of langs and apply the match function as a filter
    4$\,
    # Get the length of the array of matches and square it
    ,.*
    # Stack is [array of langs] "user" (length-votes) "lang" (num with lang)^2
    # Bring the "lang" to the top, get its length, subtract and add
    \,-+
    # Stack is [array of langs] "user" (score-length of longest lang)
    # Get an array of length of language names and sort it
    2${,}%$
    # Drop it apart from the largest value, and add that to the score
    )\;+
    # Package the "user" score from the top of the stack as [score "user"]
    [\]
}%
# Sort. Since each element is a [score "user"] value, this will sort by score.
$
# Discard the [array of langs].
\;
# Stack is an array of [score "user"] arrays. Get its length and create an array of the
# same length which counts from 0.
.,,
# Group and zip, so we go from [[score0 "user0"] ... [scoren "usern"]] [0 ... n] to
# [[[score0 "user0"] 0] ... [[scoren "usern"] n]]
]zip
# Map each [[scorei "useri"] i]
{
    # Expand, increment i (so we count from 1 rather than 0), add a space
    ~)s
    # Bring the [scorei "useri"] to the top, unpack, add a space
    @~s
    # Bring the scorei to the top, add a newline
    @n
}%
# We now have an array [[1 " " "userA" " " scoreA "\n"] ... [n " " "userZ" " " scoreZ "\n"]
# so Golfscript's standard output formatting does the rest

Peter Taylor

Posted 2011-07-18T04:55:41.140

Reputation: 41 901

That's pretty neat, I should take a look at GolfScript... I have no idea how that's parsed into something meaningful – shesek – 2011-08-18T06:52:14.827

3@shesek, added a heavily commented version – Peter Taylor – 2011-08-18T07:26:02.060

wow, very cool! thanks :-) – shesek – 2011-08-18T09:50:56.300

15

Sage: 48 42 41 non-whitespace (60246 bytes total)

Just to be a prick:

s = '   '
for c in '<lots of whitespace>'.split(s):
    s+=chr(len(c))
exec s

Note that the first line should be equivalent to s='\t', but the SE code block translates the tab to 4 spaces.

The whitespace unpacks to:

exec preparse("""
import sys
instances = {}
maxlen = 0
inputs = [line.split() for line in sys.stdin.readlines()]
for i in [0..len(inputs)-1]:
    user, language, length, votes = inputs[i]
    if language in instances:
        instances[language]+=1
    else:
        instances[language]=1
    if len(language) > maxlen:
        maxlen = len(language)

scoresheet = []
for i in [0..len(inputs)-1]:
    user, language, length, votes = inputs[i]
    length = int(length)
    votes = int(votes)
    score = length + (maxlen - len(language)) + instances[language]*instances[language] - votes
    scoresheet.append((score,user))

scoresheet.sort(reverse=False)
for user, score in scoresheet:
    print user, score""")

Note that my use of [0..len(inputs)-1] ensures that this isn't a Python script, since Sage is a superpython*. Unfortunately, exec falls back on Python... so I've gotta preparse it.

edit 1: splitting on tabs, not newlines -- what was I thinking? edit 2: made the code easier on the eyes, and recycled the splitting tab by pushing another 'newline' to the whitespace

*ok, not quite: we break xor

boothby

Posted 2011-07-18T04:55:41.140

Reputation: 9 038

10

Python, 184

That's why I love spaces.

import          sys
x = sys.stdin.read(
    ).split()
z = x [  1 : : 4  ]
for i , ( j , k
) in enumerate (
      sorted (
       zip (
        [
      int(i)
    - int(j) +
  z.count(k) ** 2
+ max(map(len, z)) -
      len(k)
  for i, j, k in
       zip (
    x[2 : : 4],
    x[3 : : 4],
         z
         )
         ],
     x[ : : 4]
         )
         ),
         1
         ):
   print i, k, j

It's much more readable!

JBernardo

Posted 2011-07-18T04:55:41.140

Reputation: 1 659

3is this supposed to be some kind of ascii art picturing something? if yes, what should it look like? – oenone – 2011-08-17T08:04:57.967

@oenone you tell me. – JBernardo – 2011-08-17T10:30:58.900

2it looks like it should, but i can't recognize anything – oenone – 2011-08-17T10:37:10.190

1@oneone neither do I... – JBernardo – 2011-08-19T02:04:46.310

7

PostgreSQL - 225 non-space characters

242 → 225: Replaced subqueries with windowing clauses.

\set QUIET 1
\t
\a
\f ' '
CREATE TEMPORARY TABLE t (u TEXT, l TEXT, c INT, v INT);
\copy t FROM PSTDIN WITH DELIMITER ' ';
SELECT row_number() OVER (ORDER BY score), *
    FROM (SELECT u,
                 c
                 + count(*) OVER (PARTITION BY l)^2
                 + max(length(l)) OVER ()
                 - length(l)
                 - v AS score
                 FROM t) AS q

tested on 9.2devel

Usage and output:

$ psql -f meta.sql < meta.in
1 UserE 33
2 UserB 37
3 UserA 103
4 UserD 496
5 UserC 503

Joey Adams

Posted 2011-07-18T04:55:41.140

Reputation: 9 929

4

Python 2 - 210 203 non-space characters

import sys
e=enumerate
n=len
l=[x.split()for x in sys.stdin.readlines()]
for i,(x,y)in e(sorted((int(x[2])-int(x[3])+n(list(y for y in l if y[1]==x[1]))**2+max(n(x[1])for x in l)-n(x[1]),i)for i, x in e(l))):print i+1,l[y][0],x

Usage and output:

$ cat meta.txt | python meta.py
1 UserE 33
2 UserB 37
3 UserA 103
4 UserD 496
5 UserC 503

user1158

Posted 2011-07-18T04:55:41.140

Reputation:

you could use only x.split() (that will also remove \n) – JBernardo – 2011-07-18T22:53:30.417

@JBernardo Cheers! Saved 7 characters. – None – 2011-07-18T22:58:06.670

You could ditch the .readlines() on sys.stdin.... for any reasonable length of input the function call won't make a difference and costs some characters. Just figured that out in another golf and thought I'd share. – arrdem – 2011-08-18T20:03:04.140

4

AWK, 277 269 non-space characters

Used in to cut 8 chars.

Spaced version and commented version:

{
        # read in user strings
        u[NR]=$0
        # count number of times language has been used
        l[$2]+=1
}

END{
        # get maximum language length
        M=0
        X=NR
        for (g in l){
                f=length(g)
                if(f>M)
                        M=f
        }
        # get score for user i
        for(i in u){
                split(u[i],c)
                s[i]=c[3]+l[c[2]]^2+M-length(c[2])-c[4]
        }
        # sort scores and users
        for(i=2;i<=X;++i){
                for(j=i;s[j-1]>s[j];--j){
                        t=s[j]
                        x=u[j]
                        s[j]=s[j-1]
                        u[j]=u[j-1]
                        s[j-1]=t
                        u[j-1]=x
                }
        }
        # output
        for(i=1;i<=X;++i){
                split(u[i],c)
                print i,c[1],s[i]
        }
}

usage:

awk -f meta.awk data.txt

jpjacobs

Posted 2011-07-18T04:55:41.140

Reputation: 3 440

used sed '/#/ d' meta.awk|sed ':a;$!N;s/\n//;ta;s/\s//g;'|wc -c for counting characters. – jpjacobs – 2011-07-20T08:56:47.333

3

Ruby, 146 characters + 4 spaces

b=$<.map &:split
puts b.map{|u,l,c,v|[b.map{|_,n|n.size}.max-l.size+b.count{|_,n|n==l}**2+eval(c+?-+v),u]}.sort.map.with_index{|(s,u),i|[i+1,u,s]*' '}

Lowjacker

Posted 2011-07-18T04:55:41.140

Reputation: 4 466

3

JavaScript, 243 chars

for(g=0,H="length",i=J.split("\n"),p=[],l={};i[H]&&p.push(a=i.pop().split(" "));)
    X=a[1],X[H]>g&&(g=X[H]),l[X]=l[X]+1||1
for(i=-1;m=p[++i];)p[i]=[m[0],+m[2]+Math.pow(l[m[1]],2)+(g-m[1][H])-m[3]]
p.sort(function(a,b){return a[1]<b[1]?-1:1}).join("\n")

Longer than most of the other solutions... but the best I could come up with in JavaScript.

Usage

Input should be in a J variable. For example, open a console and write:

J="UserA Python 100 1\nUserB Perl 30 2\nUserC Java 500 3\nUserD Brainfuck 499 4\nUserE Perl 29 5";
for(g=0,H="length",i=J.split("\n"),p=[],l={};i[H]&&p.push(a=i.pop().split(" "));)
    X=a[1],X[H]>g&&(g=X[H]),l[X]=l[X]+1||1
for(i=-1;m=p[++i];)p[i]=[m[0],+m[2]+Math.pow(l[m[1]],2)+(g-m[1][H])-m[3]]
p.sort(function(a,b){return a[1]<b[1]?-1:1}).join("\n")

CoffeScript, 177 chars

About the same logic, in CoffeScript:

g=0;H="length";l={};([A,+C+Math.pow(l[B],2)+(g-B[H])-D] for [A,B,C,D] in for a in J.split "\n" then [_,X]=a=a.split " ";X[H]>g&&g=X[H];l[X]=l[X]+1||1;a).sort((a,b)->`a[1]<b[1]?-1:1`).join "\n"

shesek

Posted 2011-07-18T04:55:41.140

Reputation: 131

I like how you abbreviate the length attribute by using a variable and subscripts. – Joey Adams – 2011-08-18T05:26:21.207

3

Common Lisp - 546

(when golfed boy consolidating parenthesis, not counting spaces)

;;;; This is an answer to Code-Golf question
;;;; 3203/meta-golf-challenge
;;;; By using Common Lisp I plan to have the longest
;;;; Language-name while I cannot hope to have the
;;;; lowest character count due to Lisp's
;;;; linguistic tradition I can avoid the 16 or 25-pt
;;;; penalty atached to being the 4th or 5th PY
;;;; based answer.

(defun f (i)
 (loop for e in y do
  (if (eq i (nth 0 e))
   (return (nth 1 e))
  )
 )
)

(setf x
 (loop for l = (read-line () () () ())
  while l collect (loop for i = 0 then (1+ j)
                   as j = (position #\Space l :start i)
                   collect (subseq l i j) while j)
 )
)

(setf y
 (loop for a in x collect
  (list
   (+
    (read-from-string (nth 2 a))
    (expt (reduce #'+ (loop for b in x collect (if (string= (nth 1 a) (nth 1 b)) 1 0) ) ) 2 )
    (+ 5 (- (reduce #'min (loop for b in x collect (length (nth 1 b)))) (length (nth 1 a))))
    (* -1 (read-from-string (nth 3 a)))
   )
   (car a)
  )
 )
)

(setf g
 (sort (loop for c in y collect (nth 0 c)) #'<)
)

(loop for i = 0 then (1+ i) while (< i (length g)) do
 (setf a (nth i g))
 (format t "~A ~A ~A~%" (1+ i) (f a) a)
)

Heavily golfed, my common lisp solution was and is the longest on the board. So I decided to cheat a bit by writing a significantly shorter bootloader and claiming that as my submission. (I consider @Boothby's submission to be a precedent in favor of this behavior)

Major thanks to Peter Taylor for his help squeezing every last char out of this bootstrapper.

BASH - 35

wget -q goo.gl/R4R54
cat -|clisp l.lsp

Usage: cat ./test0 | bash ./btstrp.sh

Joey Adams pointed out that this is not a fair solution because I can "arbitrarily increase the complexity of your solution without a corresponding increase in code size", a point not clearly expressed in the spec.

arrdem

Posted 2011-07-18T04:55:41.140

Reputation: 805

1Wouldn't a for-loop be shorter than the until? – Peter Taylor – 2011-08-18T14:26:12.967

not sure... but found a shorter while! – arrdem – 2011-08-18T14:34:22.383

1Also, if you specify the variable to read into you don't have to use $REPLY. Try while read x;do a=$x"\n"$a;done. And you should be able to remove the spaces after the |s on the last line. On another note, I'm not sure that using an internal IP address is very useful: it won't work for anyone else. – Peter Taylor – 2011-08-18T14:43:11.330

Or even wget -q http://url/l.lsp ;cat - |clisp l.lsp – Peter Taylor – 2011-08-18T14:45:57.660

Okay, you lost me on the cat - – arrdem – 2011-08-18T14:48:54.870

No, ok, that cat doesn't work: it's not hooked up to the shell's stdin. But I'm pretty sure you could move the wget to the start and then while read x;do echo $x;done|clisp l.lsp. (Sorry, don't have cygwin here so can't test until I get home). – Peter Taylor – 2011-08-18T15:12:43.663

... you are a wizard. – arrdem – 2011-08-18T15:41:11.027

@PeterTaylor let us continue this discussion in chat

– arrdem – 2011-08-18T19:04:05.233

The output is not exactly right. It should be POSITION USER POINTS – JBernardo – 2011-08-18T21:56:49.830

@jbernardo - good catch, thanks – arrdem – 2011-08-19T01:09:32.013

I don't think your code is valid because you had already posted a Lisp solution and this one require internet connection and is pretty much cheating... – JBernardo – 2011-08-19T16:47:04.713

I would argue otherwise. If you didn't notice, the highest voted solution also "cheats" by encoding the code entirely in whitespace which is not considered under the contest rules. Nor am I the first person to post a golf based on running remotely acquired code. Now, is it "cheating"? yes. Is it grounds for my POSTED code to not be scored same as everyone else's... that I leave to the OP and mods. – arrdem – 2011-08-19T22:05:27.513

@rmackenzie if you read the last lines of the question you would see that the highest voted answer is also not valid. You bash answer require the lisp answer. So, by the rules each user can have only one answer – JBernardo – 2011-08-20T00:49:50.807

2

Scala 269 266 252 without blanks and newlines.

val b = io.Source.stdin.getLines.toList.map (_.split (" "))
b.map (a => {
  val l = b.filter (_(1) .equals ( a(1))).size
  a(0) -> (a (2).toInt + l * l + (b.map (x => x(1).length).max - a(1).length) - a(3).toInt)
}).sortBy (_._2).zipWithIndex .map (m => m._2 + " " + m._1._1 + " "+ m._1._2).mkString ("\n")

Invocation:

cat user.lst | scala -i metagolf.scala

updates:

  • simplified (l => l.foo) -> (_.foo)
  • invocation
  • Gareths hint of stdin

my solution:

* 0 boothby 39
1 PeterTaylor 79
2 Lowjacker 151
* 3 JBernardo 185
4 Harpyon 207
5 JoeyAdams 220
6 shesek 241
7 userunknown 257
8 jpjacobs 273
9 rmackenzie 541

*) out of contest

user unknown

Posted 2011-07-18T04:55:41.140

Reputation: 4 210

You can use stdin instead of fromFile(System.in). – Gareth – 2011-08-19T20:42:14.243

1Thanks. Now I need 179 upvotes, and would have won the challenge - ceteris paribus. – user unknown – 2011-08-19T21:41:12.107

No problem. Hmm...not sure there's enough traffic to get you 179 upvotes... – Gareth – 2011-08-19T21:50:37.860