Quanta generosità è disponibile su StackOverflow?


33

Compito:

Sei un programmatore straordinario e risponditore StackOverflow e decidi di rispondere a ogni domanda con una generosità su StackOverflow. Sei così bravo, che riesci a ottenere tutti i doni in tutte le domande. Mentre aspetti che arrivi il rappresentante, scrivi un programma che va e scopri qual è la quantità totale di rappresentante in tutti quei doni.

Regole:

  • Quando eseguito,
    • Il tuo programma navigherà attraverso la scheda in primo piano su Stack Overflow.
    • Rascherà il valore di ogni generosità,
    • Quindi lo aggiungerà e visualizzerà il totale
  • Deve scaricare i dati da qualsiasi luogo su SO (e solo SO), ma consiglierei di utilizzare https://stackoverflow.com/questions?pagesize=50&sort=featured , in quanto sono solo circa 10 pagine
  • Questo è , quindi vince il codice più corto


2
stackoverflow.com/?tab=featured . Tutte le domande in primo piano su 1 pagina.
Nzall

7
@NateKerkhofs non è tutto. Scorrere fino alla fine. ad esempio, quando l'ho appena caricato, mostrava 96 di 472 domande.
bazzargh,


@justhalf è già stato discusso ...
TheDoctor

Risposte:


23

JavaScript - 176 133 130 108 106

function f()(t+=$("[title~=an]").text(),u=$("[rel*=x]")[0])?$("html").load(u.href,f):alert(eval(t));f(t=0)

Modifica 1: abbattuto alcuni selettori e utilizzato il ?:suggerimento del compilatore di chiusura di Google (tramite @Sirko - grazie)

Modifica 2: inizializza sdentro de inizializza tcome 0anziché""

Modifica 3: realizzato che in realtà non ho bisogno di indirizzare un contenitore specifico e posso spazzare l'intero documento, che elimina un mucchio di .findchiamate e un selettore non necessario (più la variabile che lo tiene)

Modifica 4: spingere l' tinizializzatore nella chiamata della funzione per evitare un ;(verrà comunque sollevato in alto) e comprimere la funzione su un'istruzione (combinare due istruzioni in una all'interno della condizione dell'istruzione ternaria) per eliminare{}

Nota : non sono sicuro che sia un imbroglio, ma questo deve essere eseguito da una finestra della console di un browser che punta già a http://stackoverflow.com/questions?page=1&sort=featured. Si basa sul fatto che jQuery e i collegamenti di paging appropriati sono disponibili sulla pagina stessa. Inoltre, sembra funzionare solo in Firefox e non in IE o Chrome.

Output (al momento della pubblicazione):

38150 (in an alert dialog)

Esploso / commentato :

function f()
    //concat all the bounty labels to t (they take the format "+50")
    //happens to be elements with title attribute containing word 'an'
    (t+=$("[title~=an]").text(),
    //find the "next" (has rel=next attribute) button
    u = $("[rel*=x]")[0])       
        ?
        //if there is a next button, load it, and then recurse f again
        $("html").load(u.href,f)
        :
        //else eval the 0+a+b+...+z tally and alert the result
        alert(eval(t))
//kick off the initial scrape (and simultaneously init the total tally)
f(t=0)

s=" #mainbar";d=$(s);t="";function a(){d.find(".bounty-indicator").each(function(){t+=this.innerHTML});(u=d.find("[rel=next]")[0])?d.load(u.href+s,a):alert(eval(t))}a();169 - usato Google Closure Compiler.
Sirko

8
Scelta subdola di lingua e contesto per aggirare molti dei personaggi richiesti! (Come " stackoverflow.com/" ) Mi piace!
AlexC

Penso che dovresti menzionare che è stato fatto usando il plugin jQuery. che penso dovrebbe essere .. :)
Mr_Green

Chrome genera un errore di sintassi. Aprire un corpo di funzione con un (paren, funziona davvero?
thejh

@Mr_Green - L'ho già notato, ma l'ho osato attirare più attenzione ...
Alconja,

21

Python - 232, 231, 195, 183, 176, 174

Analizza l'HTML da https://stackoverflow.com/questions?sort=featured utilizzando espressioni regolari.

Il limite superiore di rangenel forciclo deve essere number of pages + 1altrimenti il ​​codice aumenterà a HTTPErrorcausa di 404s. Il numero predefinito di risultati per pagina è 15, che è ciò che utilizza il codice (omettendo i ?pagesize=50salvataggi sui caratteri ed è altrettanto efficace).

Grazie a @Gabe per il suggerimento su come ridurre ulteriormente il conteggio dei caratteri.

Golfato :

import requests,re;print sum(sum(map(int,re.findall(r"<.*>\+(\d+)<.*>",requests.get("https://stackoverflow.com/questions?sort=featured&page=%u"%i).text)))for i in range(1,33))

Output (al momento della pubblicazione):

37700

Non golfato :

Ecco una versione in qualche modo non giocata a golf che dovrebbe essere un po 'più facile da leggere e capire.

import requests, re

print sum(
          sum(
              map( int,
                   re.findall( r"<.*>\+(\d+)<.*>",
                               requests.get( "https://stackoverflow.com/questions?sort=featured&page=%u" % i).text
                   )
              )
          ) for i in range( 1, 33 )
      )

1
Puoi sbarazzarti del forciclo esplicito e portarlo fino a 176:import urllib,re;print sum(sum(map(int,re.findall(r"<.*>\+(\d+)<.*>",urllib.urlopen("http://stackoverflow.com/questions?sort=featured&page=%u"%i).read())))for i in range(1,33))
Gabe

avere un limite superiore codificato rende un po 'difficile il test
Einacio


6
@Richard Sì, ma questo è il golf del codice , quindi la brevità supera se si tratta di una "buona idea". Voglio dire, anche in Real Life non è una buona idea scrivere orribili battute senza spazi bianchi ...
Tim Goodman,

3
@Richard L'analisi di html e l'estrazione da html sono attività piuttosto diverse. Poiché un sito Web non è un'API stabile, non è garantito il funzionamento di questo tipo di estrazione. Sebbene il codice di Tony sia un po 'troppo pieno, quindi fallirebbe se ci fosse un tag che contiene un +seguito da un numero. Ad esempio un titolo di domanda potrebbe adattarsi a quel formato.
Codici InCos

18

Rebol - 164 133 130 (139 con controllo 404)

Analizza l'html usando la parsesotto-lingua di Rebol. Controlla le prime 98 pagine. Mi sono reso conto di avere lo stesso vincolo della soluzione Python: troppe ripetizioni colpiscono errori 404 e interrompono l'esecuzione. Grazie a @rgchris per molti miglioramenti! Aggiornato per controllare fino a 98 pagine.

s: 0 repeat n 99[parse read join http://stackoverflow.com/questions?sort=featured&page= n[15[thru{>+}copy x to{<}(s: s + do x)]]]s

Con controllo errori per 404s (139):

s: 0 repeat n 99[attempt[parse read join http://stackoverflow.com/questions?sort=featured&page= n[15[thru{>+}copy x to{<}(s: s + do x)]]]]s

Test

>> s: 0 repeat n 20[parse read join http://stackoverflow.com/questions?sort=featured&page= n[15[thru{>+}copy x to{<}(s: s + do x)]]]s
== 23600

>> s: 0 repeat n 99[attempt[parse read join http://stackoverflow.com/questions?sort=featured&page= n[15[thru{>+}copy x to{<}(s: s + do x)]]]]s
Script: none Version: none Date: none
== 36050

Spiegazione

Rebol ignora gli spazi bianchi, quindi puoi mettere tutto su una riga in questo modo se lo desideri. PARSE accetta due input e il primo argomento ( read join ...) è abbastanza autoesplicativo. Ma ecco alcuni commenti sulle istruzioni dialettali di analisi, in un rientro più tradizionale:

s: 0
repeat n 99 [
    parse read join http://stackoverflow.com/questions?sort=featured&page= n [
        ;-- match the enclosed pattern 15 times (the rule will fail politely when there are less entries)
        15 [
            ;-- seek the match position up THRU (and including) the string >+
            thru {>+}
            ;-- copy contents at the current position up TO (but not including) <
            copy x to {<}
            ;-- (Basically, run some non-dialected Rebol if this match point is reached) the do is a bit dangerous as it runs the string as code
            (s: s + do x)
        ]
    ]
]
;-- evaluator returns last value, we want the value in S
;-- (not the result of PARSE, that's a boolean on whether the end of input was reached)
s

Bello ... Ho aggiunto una versione formattata originale con alcuni commenti, spero non ti dispiaccia! È sempre bello vedere come Rebol risolva così tanti problemi con tale alfabetizzazione (tutto in un eseguibile con licenza Apache multipiattaforma da mezzo mega ma che rende le cose come REFORM sporgono come un pollice dolorante Ogni altro bit ha senso ma continuo a sembrare a quella parola e vai "Riduci e FORM viene trasformato in REFORM" è semplicemente brutto . Ossessionarti è molto Hawthorne . Oh, e potresti cambiare QUALCUNO in QUALSIASI e radere un
carboncino

Oops, dovrebbe essere 133.
rgchris

Nota: è necessario passare a un nvalore superiore ... al momento ci sono 28 pagine di taglie (per dimensioni della pagina 15). Tuttavia, non influirà sul conteggio dei caratteri.
Alconja,

Grazie Alconja. Facile andare fino a 98 pagine prima di aggiungere altri caratteri alla soluzione. Stasera
dovrò ripetere

11

Ruby, 260

require'open-uri'
require'zlib'
i=b=0
d=''
until /"has_more":f/=~d
i+=1
d=Zlib::GzipReader.new(open("http://api.stackexchange.com/2.2/questions/featured?site=stackoverflow&page=#{i}&pagesize=100")).read
b+=d.scan(/"bounty_amount":(\d+)/).map{|x|x[0].to_i}.reduce :+
end
p b

Utilizza l'API di Exchange Stack.

Uscita (al momento del post originale):

37200

Non sto contando il conteggio dei &pagesize=100personaggi, perché funziona senza di esso, ma l'ho appena aggiunto per comodità durante il test. Se lo rimuovi, fa la stessa cosa (tranne che mangia più quota e impiega un po 'più di tempo).


Bene, l'ho ottenuto solo a 275 in Python
Claudiu,

mangia più quota ??? Avresti dovuto usare solo SO e SO.
John Dvorak,

@JanDvorak ??? Intendevo quota API.
Maniglia della porta

1
Le requires possono essere sostituite con il -rflag della riga di comando.
Giustino

8

Rebmu - 108 107

rtN99[parseRDrj[http://stackoverflow.com/questions?sort=featured&page=N][15[thru{>+}copyXto{<}(a+JdoX)]]]j

Test (alle 19:05 AEST)

>> rebmu [rtN99[parseRDrj[http://stackoverflow.com/questions?sort=featured&page=N][15[thru{>+}copyXto{<}(a+JdoX)]]]j]
Script: none Version: none Date: none
== 79200

Rebmu sembra piuttosto enigmatico, ma è abbastanza leggibile una volta capito. Cominciamo togliendo il fango e disponendolo correttamente.

rt n 99 [
    parse rd rj [
        http://stackoverflow.com/questions?sort=featured&page= n
    ][
        15 [
            thru {>+}
            copy x to {<}
            (a+ j do x)
        ]
    ]
]
j

Rebmu è un dialetto di Rebol in modo da poter vedere le somiglianze nella soluzione. Rebmu non può ancora ridurre le dimensioni di ogni affermazione, ma è un linguaggio in evoluzione. Grazie ancora a @rgchris per i miglioramenti al mio primo tentativo.


ti(a numero intero!) sarebbe più sicuro che doin Rebmu senza alcuna modifica della lunghezza del codice.
rgchris,

6

Rubino - 197

Versione breve:

require 'nokogiri'
require 'open-uri'
s=0
(1..33).each{|p|Nokogiri::HTML(open("http://stackoverflow.com/questions?page=#{p}&sort=featured")).css('.bounty-indicator').each{|b|s+=b.content.to_i}}
p s

Versione umana:

require 'nokogiri'
require 'open-uri'
s=0
(1..33).each do |p|
    Nokogiri::HTML(open("http://stackoverflow.com/questions?page=#{p}&sort=featured")).css('.bounty-indicator').each do |b|
        s += b.content.to_i
    end
end
puts s

E rispondi - 39700

Ruby con parametri di script - 139

require 'nokogiri'
require 'open-uri'
s=0
(1..33).each{|p|Nokogiri::HTML(open(ARGV[0]+p.to_s)).css(ARGV[1]).each{|b|s+=b.content.to_i}}
p s

Per eseguirlo da bash basta digitare

ruby code_golf_stack_overflow2.rb http://stackoverflow.com/questions?sort=featured\&page= .bounty-indicator

Le requires possono essere sostituite con il -rflag della riga di comando.
Giustino

6

PHP - 121 byte

<?for(;preg_filter('/>\+(\d+)/e','$t+=\1',@file('http://stackoverflow.com/questions?sort=featured&page='.++$n)););echo$t;

Usando un modificatore regex 'eval', per evitare di usare array_sumo simili. Sembra essere la soluzione più breve tra le voci valide.


4
il emodificatore è stato deprecato a partire da PHP 5.5, ma è comunque utile per giocare a golf.
Fabrício Matté,

6

PHP, 134 , 131 , 127

while($q=array_sum(preg_filter('#.*>\+#',0,file("http://stackoverflow.com/questions?sort=featured&page=".++$n))))$s+=$q;echo$s;

Passerà attraverso tutte le pagine, pagesizenon è impostato per salvare byte, quindi più GETs.

Molto molto sporco, ma ... sfruttando PHPi "difetti"!

  • nessuno spazio dopo echo
  • while si ferma al compito
  • l'output dopo la RegExsostituzione è una stringa che inizia con l'importo della taglia
  • array_sum() aggiunge stringhe
  • $ne $ssono inizializzati, ma partire dal nulla è equiv. come a partire da zero
  • eccetera...

5

Bash 206

ottimizzazioni possibili, troppo pigre

s=0;for i in `seq 1 11`;do for j in `wget -q -O - "http://stackoverflow.com/questions?pagesize=50&sort=featured&page=$i" | grep -o -E "bounty worth [0-9]*" | grep -o -E "[0-9]*"`;do s=$(($s+$j));done;done;echo $s

risultato:

39450

4
Potrei sbagliarmi, ma sembra che potrebbe essere molto breve con alcune ottimizzazioni di qualità.
rickcnagy,

seq 1 11può essere ridotto a seq 11.
fedorqui,

Dovresti essere in grado di sbarazzarti degli spazi attorno alle pipe per salvare quattro caratteri, e sicuramente quei due greps possono essere uniti in uno (intendevi "[0-9] +"?).
Desty,

Anche "grep -o -E" => "egrep -o".
Desty,

E puoi cambiare: "egrep -o '[0-9] +'" => "cut -d '' -f3" :)
Desty

5

Javascript - 129 119 110 107 caratteri

MODIFICA: RISPOSTA NON VALIDA! Questo gestisce solo le "Domande in primo piano", che ne contiene solo una parte. La risposta di Alconja è più valida.

s="#mainbar";t="";eval("$(s).find('.bounty-indicator').each(function(){t+=this.innerHTML});alert(eval(t))")

Eseguire su https://stackoverflow.com/?tab=featured in una finestra della console. Basato sulla soluzione di Alconja.

Golfato un po 'di più rimuovendo gli spazi bianchi non necessari.

Utilizzato eval per rimuovere la chiamata di funzione, cancellando altri 9 caratteri.

eliminato alcuni spazi bianchi non necessari.


3

Java, 540 caratteri

Attenzione: il numero di taglie attive è ~ 470. Questo codice accederà a una pagina su StackOverflow più volte. Potresti metterti nei guai con loro per aver fatto così tante richieste di dati.

import java.io.*;import java.net.*;public class B{public static void main(String[]A){String u="http://stackoverflow.com/questions",d;Long i,s=i=0L,n=i.parseLong(o(u).replaceAll("^.*b.>(\\d+).*$","$1"));while(i++<n){d=o(u+"?pagesize=1&sort=featured&page="+n).replaceAll("^.*ion.>.(\\d+).*$","$1");s+=d.matches(".*\\D.*")?0:n.parseLong(d);}System.out.print(s);}static String o(String s){String d="";try{BufferedReader r=new BufferedReader(new InputStreamReader(new URL(s).openStream()));while((s=r.readLine())!=null)d+=s;}finally{return d;}}}

Il mio output è stato 23400, ma quando ho eseguito il codice @ TonyH, ho ottenuto 37550. Cattive notizie.

Codice grazioso:

import java.io.*;
import java.net.*;

public class StackOverflowBounty {

    public static void main(String[] args) {
        String u = "http://stackoverflow.com/questions", d;
        Long i, s = i = 0L, n = i.parseLong(o(u).replaceAll("^.*b.>(\\d+).*$", "$1"));
        while (i++ < n) {
            d = o(u + "?pagesize=1&sort=featured&page=" + n).replaceAll("^.*ion.>.(\\d+).*$", "$1");
            s += d.matches(".*\\D.*") ? 0 : n.parseLong(d);
        }
        System.out.print(s);
    }

    static String o(String s) {
        String d = "";
        try {
            BufferedReader r = new BufferedReader(new InputStreamReader(new URL(s).openStream()));
            while ((s = r.readLine()) != null) {
                d += s;
            }
        } finally {
            return d;
        }
    }
}

Il modo in cui funziona è semplice. Legge dall'URL http://stackoverflow.com/questions"per determinare il numero di domande che hanno taglie (nota: se il numero aumenta, il programma fallisce, ma se diminuisce, funziona bene). Si cerca per questo numero utilizzando l'espressione regolare: b.>(\\d+). Questo ha funzionato in tutti i test fino ad oggi, ma se qualcuno ha posto una domanda che corrisponde a quella regex, potrebbe non funzionare.

Quindi, apriamo l'URL http://stackoverflow.com/questions?pagesize=1&sort=featured&page=+ current question #. In altre parole, apriamo una nuova pagina per ogni domanda in primo piano e imponiamo che il numero di domande sia solo 1, quindi le otterremo tutte. La parte della reputazione corrisponderà sempre ion.>.(\\d+), quindi la uso per trovarla. Ho diviso l'operazione in due parti in modo da poter verificare in modo economico se il numero di domande ridotto (ovvero la stringa restituita non è un numero intero).

Quindi, riassumiamo tutta la reputazione e la stampiamo.

Il mio computer ha impiegato circa 3 minuti e 20 secondi.


Qualcuno sa perché non sta stampando il numero giusto?


pagesize = 100 indica il numero elevato. Penso che stia succedendo qualcosa di strano perché stai passando pageize = 1. Nella mia risposta, se non avessi specificato 'dimensioni pagina', il risultato sarebbe stato vicino al tuo numero.
jzm

@malik Sì, mi sono reso conto che ho letto male il tuo commento, quindi ho eliminato il mio :-). pagesize = 100 si comporta come se pagesize = 50. Intendi dire che hai eseguito il mio codice con pagesize = 100?
Justin

2

C # - 407

class B{void Main(string[] a){var o=0;for(int i=1;i<11;i++){var r=((System.Net.HttpWebRequest)System.Net.HttpWebRequest.Create(new Uri(string.Format(a[0]+"&page={0}",i)))).GetResponse();if(r.ContentLength>0){using(var s=new StreamReader(r.GetResponseStream()))foreach(Match m in Regex.Matches(s.ReadToEnd(),"bounty worth (.+?) "))o+=int.Parse(m.Value.Substring(m.Value.IndexOf('h')+2));}}Console.Write(o);}}

Utilizzando Stackoverflow.com. Come di seguito, tranne la decompressione di Gzip e regex diversi.

Test

> prog.exe http://stackoverflow.com/questions?pagesize=50&sort=featured
38150

Stranamente, ottenendo un valore diverso da quello sotto.


C # - 496

Questo utilizza api.stackexchange che è gzipped e json.

using System.IO.Compression;class B{void Main(string[] a){var o=0;for(int i=1;i<11;i++){var r=((System.Net.HttpWebRequest)System.Net.HttpWebRequest.Create(new Uri(string.Format(a[0]+"&page={0}",i)))).GetResponse();if(r.ContentLength>0)using(var s=new StreamReader(new GZipStream(r.GetResponseStream(),CompressionMode.Decompress)))foreach(Match m in Regex.Matches(s.ReadToEnd(),@"bounty_amount"":(.+?),"))o+=int.Parse(m.Value.Substring(m.Value.IndexOf(':')+1).Replace(",",""));}Console.Write(o);}}

Unminified:

using System.IO.Compression;

class B
{
    void Main(string[] a)
    {
        var o = 0;
        for (int i=1; i<11; i++) {
            var w = (System.Net.HttpWebRequest)System.Net.HttpWebRequest.Create(new Uri(string.Format(a[0]+"&page={0}",i)));
            if(w.GetResponse().ContentLength > 0)
                using(var s = new StreamReader(new GZipStream(w.GetResponse().GetResponseStream(),CompressionMode.Decompress)))
                    foreach(Match m in Regex.Matches(s.ReadToEnd(), @"bounty_amount"":(.+?),"))
                        o += int.Parse(m.Value.Substring(m.Value.IndexOf(':')+1).Replace(",", ""));
        }
        Console.Write(o);
    }
}

Test

Dimensione pagine predefinita:

> prog.exe http://api.stackexchange.com/2.2/questions/featured?site=stackoverflow
25300

PageSize = 100:

> prog.exe "http://api.stackexchange.com/2.2/questions/featured?site=stackoverflow&pagesize=100"
37400

2

jQuery 191

i=0;function f(p){$.get('//api.stackexchange.com/2.2/questions/featured?site=stackoverflow&page='+p,function(d){for(x in d.items)i+=d.items[x].bounty_amount;d.has_more?f(p+1):alert(i)})};f(1)

Funziona da qualsiasi punto dello stackexchange (e di molti altri siti), non è necessario trovarsi in una pagina specifica come nelle risposte di @ Alconja / @ NateKerkhofs


jQuery è una biblioteca, non una lingua. Non sono sicuro che sia valido o no ...
rickcnagy

@ br1ckb0t prendilo come javascript se vuoi. jQuery è già sui siti di stackexchange, ero solo esplicito riguardo a$
Einacio

Sì, ha senso! Bel codice.
rickcnagy,

2

PHP - 139

golfed:

<?php
$a=file_get_contents('http://stackoverflow.com/?tab=featured');preg_match_all('/n">\+([0-9]+)<\/div>/',$a,$r);echo array_sum($r[1]);

Ungolfed - 147

Semplice file_get_contents/ preg_match/array_sum

<?php
$a = file_get_contents('http://stackoverflow.com/?tab=featured');
preg_match_all('/n">\+([0-9]+)<\/div>/', $a, $r);
echo array_sum($r[1]);

Test:

php run.php

10250


2

Bash 174

Basato su https://codegolf.stackexchange.com/a/25180/7664 :

s=0;for i in {1..11};do for j in `wget -qO- "stackoverflow.com/questions?pagesize=50&sort=featured&page=$i"|cut -d' ' -f18|egrep '^[0-9]+$'`;do s=$(($s+$j));done;done;echo $s

Puoi sbarazzartene pagesize=50&e semplicemente eseguirne un altro ciclo (penso che la dimensione della pagina predefinita sia 15).
Alconja,

@Alconja Hmm, giusto, quindi potrei arrivare a 162 ... ma solo con il rovescio della medaglia di più richieste di spam al server.
thejh

2

Python (174 caratteri):

Espandendo la risposta di Python sopra (non hai abbastanza karma per commentare):

import requests,re;print sum(sum(map(int,re.findall(r"<.*>\+(\d+)<.*>",requests.get("http://stackoverflow.com/questions?sort=featured&page=%u"%i).text)))for i in range(1,33))

Le richieste al posto di urllib riducono di 2 caratteri.


1

Rubino (176 caratteri):

Seguendo l'esempio di Tony H. di usare numeri di pagina codificati, ecco cosa ho ottenuto:

require'open-uri';b=0;(1..29).each{|i|d=open("http://stackoverflow.com/questions?sort=featured&page=#{i}").read;b+=d.scan(/<.*>\+(\d+)<.*>/).map{|x|x[0].to_i}.reduce 0,:+};p b

mi ha dato 35300 al momento della scrittura.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.