2015-07-09 61 views
4

我完全不熟悉编程。这是我的第一个“适当”项目,将被其他人使用。在文件中的某个点追加,每次增加一个值

该程序提出了各种问题,然后写入一个新的商店入口文件。对于一个空文件,我大部分都可以工作,但成品需要将条目插入现有文件中的特定点。

2问题已经我百思不得其解:

如何插入新开店项目到文件之前,“返回:”我如何增加“InventoryLocation:”通过各1项被添加

时间该文件被附加到具有这种结构:

# shop 1 
SuperSpaceSquids: 
    RewardType: playercommand 
    PriceType: free 
    Reward: 
    - ewarp Shop-SuperSpaceSquids 
    MenuItem: 
    - type:SKULL_ITEM 
    - playerhead:MHF_Squid 
    - durability:3 
    - amount:1 
    - name:&5SuperSpaceSquids 
    - 'lore:&6&o"Squid Shop From Space!"' 
    Message: '' 
    InventoryLocation: 38 
    ExtraPermission: '' 
# shop 2 
HadesKitty: 
    RewardType: playercommand 
    PriceType: free 
    Reward: 
    - ewarp Shop-HadesKitty 
    MenuItem: 
    - type:SKULL_ITEM 
    - playerhead:Turtle_Em 
    - durability:3 
    - amount:1 
    - name:&5HadesKitty 
    - 'lore:&6&o"our prices are fair!..."' 
    Message: '' 
    InventoryLocation: 39 # This value needs to be incremented by 1 each time 
    ExtraPermission: '' 
>> insert new shops here << 
Back: 
    RewardType: shop 
    PriceType: free 
    Reward: Shop_Menu 
    MenuItem: 
    - type:REDSTONE 
    - amount:1 
    - name:&cBack 
    - lore:&8Back to Shop Menu 
    InventoryLocation: 54 

这是写入到文件中的功用:

def write(shop, id, data, desc, skull): 
    f = open('file.yml', 'w') 
    f.write(" %s:" % shop) 
    f.write("\n RewardType: playercommand") 
    f.write("\n PriceType: free") 
    f.write("\n Reward:") 
    f.write("\n - ewarp shop-%s" % shop) 
    f.write("\n MenuItem:") 
    if skull: 
     f.write("\n - Type:SKULL_ITEM") 
     f.write("\n - playerhead:%s" % skull) 
     f.write("\n - durability:3") 
    if not skull: 
     f.write("\n - id:%s" % id) 
    if data: 
     f.write("\n - durability:%s" % data) 
    f.write("\n - amount:1") 
    f.write("\n - name:&5%s" % shop) 
    f.write("\n - 'lore:&6&o\"%s\"'" % desc) 
    f.write("\n Message:") 
    f.write("\n InventoryLocation:") 
    f.write("\n ExtraPermission: ''") 
    f.flush() 
    print "\nAll done." 
    print "\nHit Return to quit or 1 to add more shops." 

    while True: 
     choice = raw_input(prompt) 
     if choice == "": 
      print "\nGoodbye!" 
      f.close() 
      time.sleep(2) 
      exit(0) 
     elif choice == "1": 
      os.system('cls' if os.name == 'nt' else 'clear') 
      input() 
     else: 
      print "I dont understand that." 
+0

我想指出你的设计存在一些严重的问题,这些问题太广泛而无法在本网站上得到解答。你应该研究数据库理论,并习惯使用几个不同的数据库(我建议SQLite启动,后来Postgres)。实施它你自己*会*搞砸了。 – o11c

回答

1

这是一个很好的问题。我写了两个功能,为您提供:

insert_before_back(列表,列表)

insert_before_back需要在文件和所有你想要Back:之前添加行的列表的行的列表,那么这个返回一个列表,其中的项目添加在正确的索引中。

add_inventory(列表,字符串)

add_inventory需要的文件和店铺名称,其库存要增加的行的列表。然后它通过并将该数字递增1,并将列表中的值重置为新递增的值。它返回新行的列表。

您可以使用这些来修改您读入的行的列表,然后只是遍历列表中所有新修改的项目,并将每个项目写入具有相同名称的文件。

继承人使用这两个功能我的一个例子:

def insert_before_back(lines, thingsToAdd): 
    backIndex = lines.index('Back:\n') 
    for item in reversed(thingsToAdd): 
     lines.insert(backIndex, item) 
    return lines 

def add_inventory(lines, shopName): 
    shopFound = 0 
    for i in range(len(lines)): 
     if shopName in lines[i]: 
      shopFound = 1 
     if 'InventoryLocation:' in lines[i] and shopFound: 
      shopFound = 0 
      lineSplit = lines[i].split(': ') 
      incrementInventory = str(int(lineSplit[-1]) + 1) 
      lineSplit[-1] = incrementInventory + '\n' 
      lines[i] = ': '.join(lineSplit) 


newLines = [] 
with open('input.txt', 'r') as f: 
    inputLines = f.readlines() 
    newLines = insert_before_back(inputLines, ['Hello\n', 'From\n', 'heinst\n']) 
    add_inventory(newLines, 'HadesKitty') 

with open('output.txt', 'w') as f: 
    for line in newLines: 
     f.write(line) 
+0

谢谢!我很难确切地确定代码的功能,因为它对我而言并不熟悉,但我相信我会最终弄明白。 – cyclo

+0

@cyclo你究竟在遇到什么麻烦?并且不要忘记接受正确的答案! :) – heinst

-1

据我所知,我们不能修改一个文件的中间。

你只要有2种选择:

  1. 读取所有的文件到内存中的列表,然后修改列表,然后写所有的列表文件。

  2. (推荐)使用xml文件保存信息,但不是普通文件。因此,您可以使用很多工具来编写或读取它。

1

这是一个有趣的问题,heinst提供了一个很好的解决方案。不过我对这个架构有一些保留。以下是我看到的问题,如果这是一个非常小的项目,并且预计在有限的时间内使用,则可以忽略这些问题。

并发性和并行性问题: 如果多个用户同时尝试读取和更新清单,我们需要一个不同的解决方案。数据库可以轻松支持库存中的多个同时事务,而不是将文件系统作为持久性存储。

可扩展性问题: 随着事务总数随着时间增加,文件大小不断增加,读取整个文件并更新文件的规模也不会很好。事务将不得不使用某种方案在多个文件之间分割。

+1

根据我的经验,绝不应该使用“非常小”和“有限时间”的借口,因为有人*最终会使用它比您计划的时间更长。 – o11c

+0

我无法使用平面文件以外的任何类型的数据库。我发布的yaml文件由不支持其他类型存储选项的minecraft插件使用。 至于文件变得过大,当'InventoryLocation'达到52时,将创建一个新文件,因为游戏库存只能处理54个插槽。插槽53将成为“下一页”命令,该命令在游戏中打开新的库存窗口并加载新文件。槽54返回到前一个菜单。 – cyclo

+0

@Ramana Kandimalla这是我同时进行文件编辑的业余解决方案: http://pastebin.com/gKahzqVM – cyclo

相关问题