Implementa un accorciatore di URL


12

Gli URL stanno diventando troppo lunghi. Pertanto, è necessario implementare un algoritmo per abbreviare un URL.

io. La struttura di un URL

Un URL ha 2 parti principali: un dominio e un percorso . Un dominio è la parte dell'URL prima della prima barra. Si può presumere che l'URL non includa un protocollo. Il percorso è tutto il resto.

ii. Il dominio

Il dominio di un URL sarà qualcosa di simile: xkcd.com meta.codegolf.stackexcchhannnge.cooom. Ogni parte è separata dal periodo, ad es. In blag.xkcd.com, le parti sono "blag", "xkcd" e "com". Questo è ciò che farai con esso:

  • Se contiene più di due parti, mettere da parte le ultime due e concatenare la prima lettera del resto delle parti.

  • Quindi, concatenalo alla prima lettera fino alla penultima parte.

  • Aggiungi un punto e la seconda e la terza lettera della penultima parte.

  • Elimina l'ultima parte.

iii. Il sentiero

Il percorso sarà come: /questions/2140/ /1407/. Come prima, le "parti" sono separate da barre. Per ogni parte del percorso, eseguire:

  • Aggiungi una barra

  • Se è composto interamente da dieci cifre in base, interpretalo come un numero e converti in un numero in base 36.

  • Altrimenti, aggiungi la prima lettera della parte.

Alla fine, aggiungi una barra.

iv. Varie.

  • Questo è , quindi vince il codice più corto.
  • Il percorso può essere vuoto, ma l'URL termina sempre con una barra.
  • Non ci sarà un protocollo (ad es http://. file:///)
  • Non ci saranno mai meno di due parti nel dominio.
  • Si applicano scappatoie standard.

Esempi

In: xkcd.com/72/
Out:x.kc/20/

In: math.stackexchange.com/a/2231/
Out:ms.ta/a/1pz/

In: hello.org/somecoolcodeintrepreteriijjkk?code=3g3fzsdg32,g2/
Out:h.el/s/


Nel tuo ultimo esempio, il percorso non termina in kke tutto ciò che inizia con ?è una stringa di query, che non dovrebbe terminare con una barra? Inoltre, non tutti gli URL finiranno con una barra /, come www.something.com/path. O è irrilevante ai fini di questa sfida?
inserire nomeutentequi il

Questo è irrilevante.
ev3commander

Risposte:


0

Pyth, 93 85 byte

Lsm@+jkUTGdjb36J<zxz\/KP>zhxz\/=cJ\.pss[mhd<J_2hePJ\.<tePJ2\/;=cK\/sm+?-djkUThdysd\/K

Compilato a mano in pseudocodice pitonico:

                z = input()                     # raw, unevaluated
                G = "abcdefghijklmnopqrstuvwxyz"
                k = ""
                T = 10
L               def y(b):                       # define y as base10to36
 sm                 join(map(lambda d:
  @+jkUTGd            (join(range(T),interleave=k)+G)[d],
                                                # the join(..)+G makes "0...9a...z"
  jb36                 convert(b,36)            # returns a list of digit values in base10
J<zxz\/         J = z[:z.index("\/")]           # domain portion
KP>zhxz\/       K = z[1+z.index("\/"):][:-1]    # path portion
=cJ\.           J = J.split(".")                # splits domain into parts
pss[            no_newline_print(join(join[     # 1 join yields a list, the other a string
 mhd<J_2            map(lambda d:d[0],J[:-2]),
 hePJ               J[:-1][-1][1],
 \.                 ".",
 <tePJ2             J[:-1][-1][1:][:2],
 \/                 "\/"
;               ])
=cK\/           K = K.split("\/")
sm              print(join(map(lambda d:
 +?-djkUThdysd\/    "\/"+(d[0] if filterOut(d,join(range(T),interleave=k)) else y(int(d))),
                    # the filter will turn pure number into empty string, which is False
 K                  K)))

Infine, l'escrescenza termina ...


4

JavaScript (ES6), 149 byte

u=>u.split`/`.map((p,i)=>i?/^\d+$/.test(p)?(+p).toString(36):p[0]:(d=p.split`.`).slice(0,-1).map((s,j)=>s[l=j,0]).join``+"."+d[l].slice(1,3)).join`/`

Spiegazione

L'ho reso indipendente dalla soluzione di @ Neil ma alla fine è sembrato molto simile.

u=>
  u.split`/`.map((p,i)=>       // for each part p at index i
    i?                         // if this is not the first part
      /^\d+$/.test(p)?         // if p is only digits
        (+p).toString(36)      // return p as a base-36 number
      :p[0]                    // else return the first letter
    :
      (d=p.split`.`)           // d = domain parts
      .slice(0,-1).map((s,j)=> // for each domain part before the last
        s[l=j,0]               // return the first letter, l = index of last domain part
      ).join``
      +"."+d[l].slice(1,3)     // add the 2 letters as the final domain
  )
  .join`/`                     // output each new part separated by a slash

Test


1

JavaScript ES6, 157 byte

u=>u.split`/`.map((p,i)=>i?/^\d+$/.test(p)?(+p).toString(36):p[0]:p.split`.`.reverse().map((h,i)=>i--?i?h[0]:h[0]+'.'+h[1]+h[2]:'').reverse().join``).join`/`

Modifica: salvato 4 byte grazie a Doᴡɴɢᴏᴀᴛ.


Dovresti essere in grado di creare .split('/')e .split('.')creare modelli di stringhe
Downgoat,

@ Doᴡɴɢᴏᴀᴛ Bah, me lo sono ricordato anche io join!
Neil,

1

Python 2, 378 365 byte

Aggiornare

L'ho golfato un po '. I ~ 150 byte per la funzione base36 sono fastidiosi, ma non riesco a liberarmene fino a quando Python non ha un builtin per quello ...

def b(n):
 a=abs(n);r=[];
 while a :
    r.append('0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ'[a%36]);a//=36
 if n<0:r.append('-')
 return''.join(reversed(r or'0'))
u=raw_input();P=u.split("/")[0].split(".")
print"".join([p[0] for p in P[0:-2]]+[P[-2][0]]+["."]+list(P[-2])[1:3]+["/"]+[b(int(p))+"/"if p.isdigit()else p[0]+"/" for p in u.split(".")[-1].split("/")[1:-1]])

Vecchia versione

def b(n):
 a=abs(n)
 r=[]
 while a:
    r.append('0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ'[a%36])
    a//=36
 if n<0:r.append('-')
 return''.join(reversed(r or'0'))
u=raw_input()
P=u.split("/")[0].split(".")
s=""
if len(P)>2:
 for p in P[:-2]:s+=p[0]
s+=P[-2][0]+"."+P[0][1:3]
P=u.split(".")[-1].split("/")[1:-1]
for p in P:
 s+="/"+(b(int(p)) if p.isdigit() else p[0])
print s+"/"

Dato che Python non ha un modo integrato per convertire gli ints in una stringa 36 base, ho preso l'implementazione da numpy e l'ho ridotta. Il riposo è piuttosto semplice, dopo il lavoro lo cercherò di più. Suggerimenti sempre apprezzati nel frattempo!


0

Pyhton 2, 336 329 byte

aggiornare

riparato e più breve grazie a webwarrior

def b(a):
 r=''
 while a:
  r+=chr((range(48,58)+range(65,91))[a%36])
  a//=36
 return ''.join(reversed(r or '0'))
u=raw_input()
P=u.split('/')[0].split('.')
s=''
if len(P)>2:
 for p in P[:-2]: s+=p[0]
s+=P[-2][0]+'.'+P[0][1:3]
P=u.split('.')[-1].split('/')[1:]
for p in P: s+='/'+(b(int(p)) if p.isdigit() else p[0])
print s+'/'

originale

La versione di DenkerAffe con alcune mod: gestisci correttamente lo schema "foo / bar? Baz", inoltre, non è necessario alcun caso negativo nella funzione di conversione base36.

 def b(a):
 r=''
 while a:
  r+=('0123456789ABCDEFGHUKLMNOPQRSTUVWXYZ'[a%36])
  a//=36
 return ''.join(reversed(r or '0'))
u=raw_input()
P=u.split('/')[0].split('.')
s=''
if len(P)>2:
 for p in P[:-2]: s+=p[0]
s+=P[-2][0]+'.'+P[0][1:3]
P=u.split('.')[-1].split('/')[1:]
for p in P: s+='/'+(b(int(p)) if p.isdigit() else p[0])
print s+'/'

C'è un errore nella stringa di ricerca e l'intera riga può essere più corta:r+=chr((range(48,58)+range(65,91))[a%36])
webwarrior
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.