पायथन 781 731 605 579 चार्ट
जब मैंने पहली बार इसे देखा था, तब से बहुत अधिक और बहुत बेहतर उत्तर हैं, लेकिन मैंने अपनी अजगर स्क्रिप्ट पर बहुत समय बर्बाद किया है इसलिए मैं इसे किसी भी तरह से पोस्ट करने जा रहा हूं, इसे और छोटा करने के लिए सुझावों को देखना भयानक होगा,
संपादित करें: एड एच के सुझावों के लिए धन्यवाद 2 चार्ट कटा हुआ, आगे जाने के लिए मुझे बहुत सी चीज़ों का पुनर्गठन करना पड़ सकता है जो कि कुछ समय लेने वाला है
s="e |nd|-We| a|-(Ooh|N| what|ive| go|ay it-|I|er|G|o |make5 |D| th| othH |A| tF|ing |nna |tell|'s been|'rS|-You|-N4| know|L5 up|PR | you|evHK>| how I'm feeling-|O, g7)|O)9gL, n4gL-(G7)|-I just wa>=53Gotta EuRHstaR-.|Q've8n eachBfor sFlong:r heart<Pch?but:;toFshy@sJInsidSwSboth8M<K?onQ8CSgame6we;go>plJ|9g79let5 down9runProuR6desHt59Ecry9sayKodbye9=P lie6hurt5-|\n|Q;nFstrangHs@love:8CSrules6sFdFI-A full commitment'sM I'mCink?of: wouldn't getCis fromPnyBguy0/AR if5Psk me3Don't = me5;toFbliR@see-..2211-/0..";i=83
exec"x,s=s.split('|',1);s=s.replace(chr(i),x);i-=1"*39
print s
पहली बार जब मैंने मैन्युअल रूप से स्ट्रिंग (बहुत थकाऊ) का उत्पादन किया था, तो मैंने पैटर्न को बदलने के लिए पुनरावर्ती रूप से खोजने के लिए एक फ़ंक्शन लिखा था जो कि सबसे अधिक लाभदायक था (उस चरण में), जिसने मुझे एक समाधान दिया लेकिन यह आकार में 10 की वृद्धि करने के लिए निकला। वर्ण।
इसलिए, मैंने अपने एल्गोरिथ्म को केवल 'वर्णों को कम' करने पर अंतिम रैंकिंग करने के बजाय थोड़ा कम लालची बना दिया, 'वर्णों की कमी', 'पैटर्न की लंबाई' और 'पैटर्न के मायने' के आधार पर रैंकिंग की।
पैटर्न की लंबाई = लंबाई की गिनती = गिनती
rank = [(length-1)*count - length - 2] + lengthWeight * length + countWeight * count
फिर मैंने अपने गरीब लैपटॉप को असीम रूप से चलाने, यादृच्छिक मानों को निर्दिष्ट करने lengthWeight
और countWeight
विभिन्न अंतिम संपीड़न आकार प्राप्त करने के लिए कहा , और एक फ़ाइल में न्यूनतम संपीड़न आकारों के लिए डेटा संग्रहीत किया
आधे घंटे में या तो यह उपरोक्त स्ट्रिंग के साथ आया (मैंने इसके साथ छेड़छाड़ करने की कोशिश की कि क्या मैं कोड को छोटा कर सकता हूं), और यह किसी भी कम नहीं होगा, मुझे लगता है कि मुझे यहां कुछ याद आ रहा है।
इसके लिए यहां मेरा कोड, यह भी max_pattern
बहुत धीमा है (नोट: कोड समाधान के मेरे पिछले संस्करण में फार्म के समान एक स्ट्रिंग को थूकता है, मैंने वर्तमान रूप को प्राप्त करने के लिए मैन्युअल रूप से काम किया, मैन्युअल रूप से मेरा मतलब है, मैन्युअल रूप से अजगर खोल में)
import itertools
global pretty
global split
split = False
pretty = False
# try to keep as much visibility as possible
def prefrange():
return range(32,127) + ([] if pretty else ([10, 9, 13] + [x for x in range(32) if x not in (10, 9, 13)] + [127]))
def asciichr():
return [chr(x) for x in prefrange()]
def max_pattern(s, o, lenw, numw):
l = len(s)
patts = []
for c in range(l/2+1,1,-1):
allsub = [s[i:i+c] for i in range(0, l, c)]
subcounts = [[a, s.count(a)] for a in allsub if len(a) == c]
repeats = [(x, y, ((c-o)*y - o*2 - c)) for x, y in subcounts if y > 1]
ranks = [(x, y, (z + lenw*c + numw*y)) for x,y,z in repeats if z > 0]
patts = patts + ranks
try:
return sorted(patts, key=lambda k: -k[2])[0]
except:
return None
def sep():
return '~~' if pretty else chr(127) + chr(127)
def newcharacter(s):
doable = [x for x in asciichr() if x not in s]
if len(doable) == 0:
doable = list(set(x+y for x in asciichr() for y in asciichr() if x+y not in s and x+y != sep()))
if len(doable) == 0:
return None
return doable[0]
def joined(s, l):
one = [x for x in l if len(x)==1]
two = [x for x in l if len(x)==2]
return ''.join(reversed(two)) + sep() + ''.join(reversed(one)) + sep() + s
def compress(s, l=[], lenw=0, numw=0):
newchr = newcharacter(s)
if newchr == None:
if not l:
return s
return joined(s,l)
else:
ptn = max_pattern(s, len(newchr), lenw, numw)
if ptn == None:
if not l:
return s
return joined(s, l)
s = s.replace(ptn[0], newchr)
s = ptn[0] + newchr + s
l.append(newchr)
return compress(s, l, lenw, numw)
def decompress(s):
lst2, lst, s = s.split(sep(),2)
li = [lst2[i:i+2] for i in xrange(0, len(lst2), 2)]+list(lst)
for c in li:
x, s = s.split(c, 1)
s = s.replace(c, x)
return s
def test(times):
import random
rnd = random.random
tested = {(1001, 1001): (10000, 10, False),}
org = open('text').read()
minfound = 1000
for i in xrange(times):
l,n = 1001,1001
while (l,n) in tested:
# i guess this would be random enough
xr = lambda: random.choice((rnd(), rnd()+rnd(), rnd()-rnd(), rnd()*random.choice((10,100,1000)), -1*rnd()*random.choice((10,100,1000)),))
n = xr()
l = xr()
sm = compress(org, l=[], lenw=l, numw=n)
try:
dc = decompress(sm)
except:
tested[l,n] = (len(sm), len(sm)/float(len(org)), 'err')
continue
tested[l,n] = (len(sm), len(sm)/float(len(org)), dc==org)
if len(sm) < minfound:
minfound = len(sm)
open('min.txt','a').write(repr(tested[l,n])+'\n')
print '~~~~~~~!!!!!!! New Minimum !!!!!!!~~~~'
return tested
if __name__ == '__main__':
import sys
split = False
try:
if sys.argv[2] == 'p':
pretty = True
except:
pretty = False
org = open(sys.argv[1]).read()
try:
l=float(sys.argv[3])
n=float(sys.argv[4])
except:
l,n=0,0
sm = compress(org,lenw=l,numw=n)
print 'COMPRESSED -->'
print sm, len(sm)
#open('new.py','w').write(sm)
print len(sm)/float(len(org))
print 'TRYING TO REVERT -->'
dc = decompress(sm)
#print dc
print dc==org