os_memory
#!/usr/bin/python
#coding=utf8
import sys
from utils import directSelectSort, col_decorate, BaseError
class MEMStoreError(BaseError):
pass
class InputError(BaseError):
pass
class Elem(object):
def __init__(self, name, s, e):
self.name = name
self.s = s
self.e = e
def __gt__(self, o):
return self.s > o.s
def __lt__(self, o):
return self.s < o.s
def __str__(self):
return '<%s, %s>' % (self.s, self.e)
class MEM(object):
size = 128
def __init__(self):
self.blocks = []
def get_frees(self):
b = self.blocks
frees = []
if 1 == len(b):
frees.append(
(0, b[0].s-0))
frees.append(
(b[0].e+1, self.size-1-b[0].e))
pass
elif 2 == len(b):
frees.append(
(0, b[0].s-0))
frees.append(
(b[0].e+1, b[1].s-1-b[0].e))
frees.append(
(b[1].e+1, self.size-1-b[1].e))
pass
elif 3 <= len(b):
frees.append(
(0, b[0].s-0))
for i in range(len(b)):
if not i == len(b)-1:
frees.append(
(b[i].e+1, b[i+1].s-1-b[i].e))
else:
frees.append(
(b[i].e+1, self.size-1-b[i].e))
else:
frees.append(
(0, self.size))
return frees
def insert(self, n, l):
b = self.blocks
# initial insert
if not b:
if l <= self.size:
elem = Elem(n, 0, l-1)
b.append(elem)
else:
raise MEMStoreError('Too large to insert')
# normal insert
else:
# calculate frees
able = False
frees = self.get_frees()
for start, length in frees:
if length >= l:
print 'insert'
self.blocks.append(Elem(n, start, start+l-1))
able = True
break
if not able:
raise MEMStoreError('Storage overflow, unable to insert')
# sort
directSelectSort(self.blocks, 's-b')
def release(self, name):
for loop, i in enumerate(self.blocks):
if name == i.name:
self.blocks.pop(loop)
do_release = True
break
class Display:
fmt = '| {0:<12}| {1:<12}| {2:<12}| {3:<12}|'
sepline = ('+'+'-'*13)*4+'+'
solidline = '|'+' '*55+'|'
def list(self):
print ''
print col_decorate('Storage list', 'blue')
print self.Display.sepline
print self.Display.fmt.format('Name', 'Size', 'Start Point', 'End Point')
print self.Display.sepline
for i in self.blocks:
print self.Display.fmt.format(i.name, i.e-i.s, i.s, i.e)
print self.Display.sepline
def present(self, row=8):
size = self.size
col = size/row
op = ''
avaliables = []
for start, length in self.get_frees():
for i in range(length):
avaliables.append(start+i)
for j in range(size):
if j in avaliables:
op += '0 '
else:
op += '1 '
if (j+1)%col == 0 and j != size-1:
op += '\n'
print ''
print col_decorate('Memory usage present', 'blue')
print op
if '__main__' == __name__:
def mode_input():
try:
print ''
print col_decorate('Menu choices', 'blue')
print '1 :: insert into mem'
print '2 :: release from mem'
print '3 :: list data name & size'
print '4 :: output memory presentation'
print '0 :: exit'
print 'Select:',
return int(raw_input())
except ValueError:
raise InputError('Mode input error')
def name_input(mode, mem):
while True:
print 'input name:',
name = raw_input()
InputError.assertTrue(name, 'Could not be None')
if 1 == mode:
if name in [i.name for i in mem.blocks]:
raise InputError('Name dumplicated')
if 2 == mode:
if not name in [i.name for i in mem.blocks]:
raise InputError('Name does not exist')
return name
def length_input():
while True:
print 'input length:',
length = int(raw_input())
InputError.assertTrue(length >= 1, 'Lenght should be >= 1')
return length
# start
mem = MEM()
while True:
try:
mode = mode_input()
if 1 == mode:
name = name_input(mode, mem)
length = length_input()
mem.insert(name, length)
elif 2 == mode:
name = name_input(mode, mem)
mem.release(name)
elif 3 == mode:
mem.list()
elif 4 == mode:
mem.present()
elif 0 == mode:
print 'exit'
sys.exit()
else:
raise InputError('No that mode')
except BaseError as e:
print e
except KeyboardInterrupt:
print col_decorate('\nexit', 'blue')
sys.exit()