आपका कार्यक्रम मूल्यवान खनिजों के लिए भूमिगत खोज करने वाले खनन रोबोट को नियंत्रित करेगा। आपका रोबोट उस नियंत्रक को बताएगा जहां आप स्थानांतरित करना चाहते हैं और खोदना चाहते हैं, और नियंत्रक आपके रोबोट की स्थिति पर प्रतिक्रिया प्रदान करेगा।
प्रारंभ में आपके रोबोट को पहले से मौजूद कुछ खनन शाफ्ट के साथ खदान का एक छवि मानचित्र दिया जाएगा, और खदान में खनिजों के मूल्य और कठोरता को निर्दिष्ट करने वाली एक डेटा फ़ाइल। आपका रोबोट तब खदानों के माध्यम से खदान में मूल्यवान खनिजों की तलाश करेगा। आपका रोबोट पृथ्वी के माध्यम से खुदाई कर सकता है, लेकिन हार्ड रॉक द्वारा धीमा हो जाता है।
24 घंटे की शिफ्ट के बाद सबसे मूल्यवान कार्गो के साथ लौटने वाला रोबोट विजेता होगा। यह एक जटिल चुनौती हो सकती है, लेकिन एक बुनियादी खनन रोबोट बनाना आसान है (नीचे नमूना खनन रोबोट उत्तर देखें)।
ऑपरेशन
आपका कार्यक्रम नियंत्रक द्वारा खान छवि, खनिज डेटा और उपकरण फ़ाइल नाम के साथ शुरू किया जाएगा। रोबोट मूल्यवान अयस्क को खोजने और कठोर चट्टान से बचने के लिए खान छवि और खनिज डेटा का उपयोग कर सकते हैं। रोबोट उपकरण सूची से उपकरण खरीदना भी चाह सकता है।
उदाहरण के लिए: python driller.py mineimage.png minerals.txt equipmentlist.txt
2 सेकंड के प्रारंभिक काल के बाद, नियंत्रक स्टड और स्टडआउट के माध्यम से रोबोट प्रोग्राम के साथ संचार करता है। स्थिति संदेश प्राप्त करने के बाद रोबोट को 0.1 सेकंड के भीतर कार्रवाई का जवाब देना चाहिए।
प्रत्येक मोड़, नियंत्रक रोबोट को एक स्थिति रेखा भेजता है:
timeleft cargo battery cutter x y direction
उदाहरण के लिए: 1087 4505 34.65 88.04 261 355 right
पूर्णांक timeleft
वह गेम सेकंड है जिसे शिफ्ट के अंत से पहले छोड़ दिया जाता है। आपके
cargo
द्वारा उपकरण के लिए भुगतान किए गए खनिजों का पूर्णांक मान अभी तक कम है। battery
स्तर अपने शेष बैटरी चार्ज के एक पूर्णांक प्रतिशत है। cutter
पूर्णांक स्तर मानक मूल्य के एक प्रतिशत के रूप में कटर की वर्तमान तीखेपन है। x
और y
मूल्यों (0, 0) पर ऊपरी बाएं कोने से संदर्भित रोबोट स्थिति के साथ सकारात्मक पूर्णांक हैं। दिशा वर्तमान दिशा है जो रोबोट सामना कर रहा है (बाएं, दाएं, ऊपर, नीचे)।
जब आपका रोबोट 'एंडशिफ्ट' या 'विफल' इनपुट प्राप्त करता है, तो आपका प्रोग्राम जल्द ही समाप्त हो जाएगा। आप चाहते हैं कि आपका रोबोट पहले फ़ाइल में डिबगिंग / प्रदर्शन डेटा लिख सके।
नियंत्रक द्वारा स्वीकृत 4 संभावित आदेश हैं। direction
left|right|up|down
उस दिशा में अपने रोबोट को इंगित करेगा, और 15 गेम-सेकंड की आवश्यकता होगी। move <integer>
आपके रोबोट को स्थानांतरित करने या खुदाई करने के लिए कई इकाइयों को निर्देश देगा जो खनिजों की कठोरता और आपके कटर के तीखेपन (नीचे देखें) के आधार पर आगे समय लेता है। buy <equipment>
निर्दिष्ट उपकरण स्थापित करेगा और आपके कार्गो मूल्य से लागत में कटौती करेगा, लेकिन केवल अगर रोबोट सतह पर है (y मान <= शुरुआती y मान)। उपकरण स्थापना में 300 गेम-सेकंड लगते हैं। विशेष कमांड snapshot
डिस्क पर वर्तमान खदान की छवि को लिखता है और कोई गेम समय नहीं लेता है। आप अपने रोबोट को डीबग करने या एनिमेशन बनाने के लिए स्नैपशॉट का उपयोग कर सकते हैं।
आपका रोबोट 100 बैटरी और 100 कटर तीखेपन के साथ शुरू होगा। चलती और मुड़ती बैटरी की थोड़ी मात्रा का उपयोग करते हैं। खुदाई अधिक उपयोग करता है और खनिजों की कठोरता और कटर की वर्तमान तीक्ष्णता का एक कार्य है। जैसा कि आपका रोबोट खनिजों में खोदता है, कटर समय और खनिजों की कठोरता के आधार पर अपना तेज खो देगा। यदि आपके रोबोट में पर्याप्त कार्गो मूल्य है, तो यह एक नई बैटरी या कटर खरीदने के लिए सतह पर लौट सकता है। ध्यान दें कि उच्च गुणवत्ता वाले उपकरणों में 100% से अधिक की प्रारंभिक प्रभावशीलता है। बैटरियों के नाम में स्ट्रिंग "बैटरी" है और (आश्चर्य) कटर के नाम में "कटर" है।
निम्नलिखित रिश्ते चलते और काटने को परिभाषित करते हैं:
timecutting = sum(hardness of pixels cut) * 100 / cutter
cutterwear = 0.01 for each second cutting
cutters will not wear below 0.1 sharpness
timemoving = 1 + timecutting
batterydrain = 0.0178 for each second moving
changing direction takes 15 seconds and drains 0.2 from the battery
installing new equipment takes 300 seconds
ध्यान दें कि किसी भी खनिज को काटे बिना 1 इकाई को हिलाने पर 1 खेल दूसरा होता है और बैटरी का 0.0178 का उपयोग करता है। तो रोबोट 93 खेल मिनटों में मानक 100 चार्ज पर 5600 यूनिट चला सकता है, अगर वह खनिजों को नहीं काट रहा हो या मोड़ रहा हो।
नई: रोबोट 11 पिक्सेल चौड़ा है, इसलिए आंदोलन के प्रत्येक पिक्सेल के साथ 11 पिक्सेल तक कट जाएगा। अगर काटने के लिए 11 पिक्सेल से कम हैं, तो रोबोट को स्थानांतरित करने में कम समय लगेगा, और कटर पर कम पहनने का कारण होगा। यदि खनिज डेटा फ़ाइल में पिक्सेल रंग निर्दिष्ट नहीं है, तो यह शून्य कठोरता और शून्य मान का निःशुल्क स्थान है।
समय समाप्त होने पर रन समाप्त हो जाता है, रोबोट बैटरी समाप्त हो जाती है, रोबोट का एक हिस्सा छवि सीमा से अधिक हो जाता है, एक अवैध कमांड भेजा जाता है, या रोबोट संचार समय से बाहर हो जाता है।
आपका स्कोर रोबोट कार्गो का अंतिम मूल्य है। नियंत्रक आपके स्कोर और अंतिम मानचित्र छवि को आउटपुट करेगा। आपके प्रोग्राम का stderr आउटपुट robot.log फ़ाइल में लॉग इन है। यदि आपका रोबोट मर जाता है, तो लॉग में घातक त्रुटि हो सकती है।
द माइन डेटा
equipment.txt:
Equipment_Name Cost Initial_Value
std_cutter 200 100
carbide_cutter 600 160
diamond_cutter 2000 250
forcehammer_cutter 7200 460
std_battery 200 100
advanced_battery 500 180
megapower_battery 1600 320
nuclear_battery 5200 570
mineraldata.txt:
Mineral_Name Color Value Hardness
sandstone (157,91,46) 0 3
conglomerate (180,104,102) 0 12
igneous (108,1,17) 0 42
hard_rock (219,219,219) 0 15
tough_rock (146,146,146) 0 50
super_rock (73,73,73) 0 140
gem_ore1 (0,255,0) 10 8
gem_ore2 (0,0,255) 30 14
gem_ore3 (255,0,255) 100 6
gem_ore4 (255,0,0) 500 21
मेरी छवि:
मेरी छवि में एक अल्फा चैनल हो सकता है, लेकिन इसका उपयोग नहीं किया जाता है।
नियंत्रक
नियंत्रक को 2.7 पायथन के साथ काम करना चाहिए और पीआईएल लाइब्रेरी की आवश्यकता है। मुझे सूचित किया गया है कि पीआईएल छवि मॉड्यूल प्राप्त करने के लिए पायथन तकिया एक विंडोज फ्रेंडली डाउनलोड है।
वर्तमान निर्देशिका में रोबोट प्रोग्राम, cfg.py, छवि और डेटा फ़ाइलों के साथ नियंत्रक प्रारंभ करें। सुझाई गई कमांड लाइन है:
python controller.py [<interpreter>] {<switches>} <robotprogram>
उदाहरण के लिए: python controller.py java underminer.class
कंट्रोलर एक रोबोट.लॉग फाइल और रन के अंत में एक फाइनलम.पिंग फाइल लिखेगा।
#!/usr/bin/env python
# controller.py
# Control Program for the Robot Miner on PPCG.
# Tested on Python 2.7 on Ubuntu Linux. May need edits for other platforms.
# V1.0 First release.
# V1.1 Better error catching
import sys, subprocess, time
# Suggest installing Pillow here if you don't have PIL already
from PIL import Image, ImageDraw
from cfg import *
program = sys.argv[1:]
calltext = program + [MINEIMAGE, MINERALFILE, EQUIPMENTFILE]
errorlog = open(ERRORFILE, 'wb')
process = subprocess.Popen(calltext,
stdin=subprocess.PIPE, stdout=subprocess.PIPE, stderr=errorlog)
image = Image.open(MINEIMAGE)
draw = ImageDraw.Draw(image)
BLACK, ORANGE, WHITE = (0,0,0), (255,160,160), (255,255,255)
W,H = image.size
dirmap = dict(right=(1,0), left=(-1,0), up=(0,-1), down=(0,1))
# read in mineral file (Name, Color, Value, Hardness):
data = [v.split() for v in open(MINERALFILE)][1:]
mineralvalue = dict((eval(color), int(value)) for
name, color, value, hard in data)
hardness = dict((eval(color), int(hard)) for
name, color, value, hard in data)
# read in the equipment list:
data = [v.split() for v in open(EQUIPMENTFILE)][1:]
equipment = dict((name, (int(cost), float(init))) for
name, cost, init in data)
# Set up simulation variables:
status = 'OK'
rx, ry, direction = START_X, START_Y, START_DIR # center of robot
cargo, battery, cutter = 0, 100.0, 100.0
clock = ENDSHIFT
size = ROBOTSIZE / 2
msgfmt = '%u %u %u %u %u %u %s'
snapnum = 1
def mkcutlist(x, y, direc, size):
dx, dy = dirmap[direc]
cx, cy = x+dx*(size+1), y+dy*(size+1)
output = [(cx, cy)]
for s in range(1, size+1):
output += [ (cx+dy*s, cy+dx*s), (cx-dy*s, cy-dx*s)]
return output
def send(msg):
process.stdin.write((msg+'\n').encode('utf-8'))
process.stdin.flush()
def read():
return process.stdout.readline().decode('utf-8')
time.sleep(INITTIME)
while clock > 0:
try:
start = time.time()
send(msgfmt % (clock, cargo, battery, cutter, rx, ry, direction))
inline = read()
if time.time() - start > TIMELIMIT:
status = 'Move timeout'
break
except:
status = 'Robot comslink failed'
break
# Process command:
movecount = 0
try:
arg = inline.split()
cmd = arg.pop(0)
if cmd == 'buy':
if ry <= START_Y and arg and arg[0] in equipment:
cost, initperc = equipment[arg[0]]
if cost <= cargo:
cargo -= cost
if 'battery' in arg[0]:
battery = initperc
elif 'cutter' in arg[0]:
cutter = initperc
clock -= 300
elif cmd == 'direction':
if arg and arg[0] in dirmap:
direction = arg[0]
clock -= 15
battery -= 0.2
elif cmd == 'move':
if arg and arg[0].isdigit():
movecount = abs(int(arg[0]))
elif cmd == 'snapshot':
image.save('snap%04u.png' % snapnum)
snapnum += 1
except:
status = 'Robot command malfunction'
break
for move in range(movecount):
# check image boundaries
dx, dy = dirmap[direction]
rx2, ry2 = rx + dx, ry + dy
print rx2, ry2
if rx2-size < 0 or rx2+size >= W or ry2-size < 0 or ry2+size >= H:
status = 'Bounds exceeded'
break
# compute time to move/cut through 1 pixel
try:
cutlist = mkcutlist(rx2, ry2, direction, size)
colors = [image.getpixel(pos)[:3] for pos in cutlist]
except IndexError:
status = 'Mining outside of bounds'
break
work = sum(hardness.get(c, 0) for c in colors)
timetaken = work * 100 / cutter
cutter = max(0.1, cutter - timetaken / 100)
clock -= 1 + int(timetaken + 0.5)
battery -= (1 + timetaken) / 56
if battery <= 0:
status = 'Battery exhausted'
break
cargo += sum(mineralvalue.get(c, 0) for c in colors)
draw.rectangle([rx-size, ry-size, rx+size+1, ry+size+1], BLACK, BLACK)
rx, ry = rx2, ry2
draw.rectangle([rx-size, ry-size, rx+size+1, ry+size+1], ORANGE, WHITE)
if clock <= 0:
break
if status != 'OK':
break
del draw
image.save('finalmine.png')
if status in ('Battery exhausted', 'OK'):
print 'Score = %s' % cargo
send('endshift')
else:
print 'Error: %s at clock %s' % (status, clock)
send('failed')
time.sleep(0.3)
process.terminate()
लिंक की गई कॉन्फ़िगर फ़ाइल (नहीं बदली जानी चाहिए):
# This is cfg.py
# Scenario files:
MINEIMAGE = 'testmine.png'
MINERALFILE = 'mineraldata.txt'
EQUIPMENTFILE = 'equipment.txt'
# Mining Robot parameters:
START_X = 270
START_Y = 28
START_DIR = 'down'
ROBOTSIZE = 11 # should be an odd number
ENDSHIFT = 24 * 60 * 60 # seconds in an 24 hour shift
INITTIME = 2.0
TIMELIMIT = 0.1
ERRORFILE = 'robot.log'
उत्तर प्रारूप
जवाब में प्रोग्रामिंग भाषा, रोबोट का नाम और अंतिम स्कोर (जैसे पायथन 3 , टनल टेरर , 1352 ) सहित एक शीर्षक होना चाहिए । उत्तर निकाय में आपका कोड और अंतिम खदान मानचित्र छवि होनी चाहिए। अन्य छवियों या एनिमेशन का भी स्वागत है। विजेता सर्वश्रेष्ठ स्कोर वाला रोबोट होगा।
अन्य नियम
- आम खामियों को निषिद्ध है।
- यदि आप एक यादृच्छिक संख्या जनरेटर का उपयोग करते हैं, तो आपको अपने प्रोग्राम में एक बीज को हार्डकोड करना चाहिए, ताकि आपका प्रोग्राम रन प्रजनन योग्य हो। किसी और को आपके प्रोग्राम को चलाने और उसी अंतिम खान छवि और स्कोर को प्राप्त करने में सक्षम होना चाहिए।
- आपका प्रोग्राम किसी भी माइन इमेज के लिए प्रोग्राम होना चाहिए । आपको इन डेटा फ़ाइलों या इस छवि आकार, खनिज लेआउट, सुरंग लेआउट, आदि के लिए अपने कार्यक्रम को कोड नहीं करना चाहिए । अगर मुझे संदेह है कि एक रोबोट इस नियम को तोड़ रहा है, तो मैं खान छवि और / या डेटा फ़ाइलों को बदलने का अधिकार सुरक्षित रखता हूं।
संपादित करता
- 0.1 सेकंड रेस्पॉन्स नियम समझाया।
- रोबोट पर कमांड लाइन विकल्प और फाइलें शुरू करने का विस्तार।
- बेहतर त्रुटि पकड़ने के साथ नया नियंत्रक संस्करण जोड़ा गया।
- जोड़ा गया Robot.log नोट।
- डिफ़ॉल्ट खनिज कठोरता और मूल्य समझाया।
- समझाया बैटरी बनाम कटर उपकरण।
- रोबोट का आकार 11 स्पष्ट किया गया।
- समय, कटर पहनने और बैटरी के लिए गणना जोड़ा गया।