Sfoglia il codice sorgente

Initial commit of code. Probably already complete

Just wanted to get this up on github.
Lily Carpenter 12 anni fa
parent
commit
f91ab0f2e0
3 ha cambiato i file con 225 aggiunte e 0 eliminazioni
  1. 8 0
      crc.py
  2. 116 0
      reddit.py
  3. 101 0
      sample.txt

+ 8 - 0
crc.py

@@ -0,0 +1,8 @@
1
+import zlib
2
+
3
+x = zlib.crc32('banana stand') & 0xffffffff
4
+y = x
5
+binary = bin(x)
6
+
7
+y = y >> binary.count('1')
8
+print y

+ 116 - 0
reddit.py

@@ -0,0 +1,116 @@
1
+# Lily Carpenter
2
+# lily-redditchallenge@azrazalea.net
3
+# 2049 South Florence Apt. 8
4
+# Springfield, MO
5
+# 417-379-3326
6
+#
7
+# Premise:
8
+# While I'm sure there is a fancy algorithm to do this very efficiently, I have not gotten far enough into
9
+# math/computer science theory in order to be able to come up with it effectively.
10
+#
11
+# Therefore, here is how my script works:
12
+# 1. Sorts all panels in descending order based on value
13
+# 2. Starting with the person with the highest yield (me) and going from there
14
+#    it adds the highest value panels to the set panel list until we reach or surpass goal
15
+# 3. If we managed to hit goal exactly, we are done. Otherwise, start second process
16
+# 4. In the second process we resort data in ascending order and try until we reach or surpass goal
17
+#
18
+# This should theoretically result in using the lower yield people the least, as well as getting as close as possible
19
+# to the goal without going over.
20
+
21
+import argparse
22
+import sys
23
+import locale
24
+
25
+# Setup command line arguments
26
+# I did goal and days partly just because I wanted to play with the values
27
+parser = argparse.ArgumentParser(description='Determine panel distribution')
28
+parser.add_argument('file_name', metavar='<File Name>', type=str, help='file containing panel data')
29
+parser.add_argument('-g', '--goal', metavar='<Goal>', type=int, help='Goal we are trying to reach (default 250000)', default=250000)
30
+parser.add_argument('-d', '--days', metavar='<Days>', type=int, help='Number of days to reach goal (default 7)', default=7)
31
+
32
+
33
+# A list of dictionaries containing the necessary data on each person
34
+# Also stores the set of panels to be assigned to each person
35
+# This is pulled from the problem description, of course
36
+people = [
37
+        {'name': 'M', 'yield': 1, 'pan_a_day': 1, 'panels': [] },
38
+        {'name': 'GM', 'yield': .95, 'pan_a_day': 2, 'panels': [] },
39
+        {'name': '?', 'yield': .85, 'pan_a_day': 3, 'panels': [] },
40
+        {'name': 'GB', 'yield': .6, 'pan_a_day': 4, 'panels': [] },
41
+    ]
42
+
43
+# Simple function, simply loads data from file_name and converts it to int, puts in list data, and returns data
44
+# The data list contains tuples of (index, value) to preserve original index later when sorting
45
+# If it gets something that isn't a number it'll tell you about it, make that entry 0, then continue like nothing happened
46
+def get_data(file_name):
47
+    data = []
48
+    with open(file_name, 'r') as _file:
49
+        for line_num, line in enumerate(_file, 1):
50
+            try:
51
+                line = int(line)
52
+            except ValueError:
53
+                sys.stderr.write('Skipping invalid data at line: ' + str(line_num) + '\n')
54
+                # This is so that we don't miss a panel index
55
+                data.append(0)
56
+            else:
57
+                data.append((line_num - 1, int(line)))
58
+    return data
59
+
60
+# Grab the data and arguments
61
+args = parser.parse_args()
62
+data = get_data(args.file_name)
63
+days = args.days
64
+goal = args.goal
65
+
66
+# Grab replacement cost of panels
67
+replace_cost = data.pop(0)[1]
68
+
69
+# Sort by the 'value' column, descending, to get list ready for processing
70
+data.sort(key=lambda datem: datem[1], reverse=True)
71
+
72
+current_money = 0
73
+panel = 0
74
+# This loop goes through each person, people is already setup to be descending by yield
75
+for person in people:
76
+    for x in range(0, person['pan_a_day'] * days):
77
+        # This is how much the current panel is worth, taking into account yield and
78
+        # replacement cost
79
+        additional_amt = data[panel][1] * person['yield'] - replace_cost
80
+
81
+        # If the next panel in list does not meet or go past the goal, add to person's panel set
82
+        # and increment current_money by additional_amt
83
+        if current_money + additional_amt <= goal:
84
+            current_money += additional_amt
85
+            person['panels'].append((data[panel][0], data[panel][1]))
86
+            panel += 1
87
+        # Otherwise, we need to switch gears and look for the smallest possible panel to finish
88
+        else:
89
+            data.sort(key=lambda datem: datem[1])
90
+
91
+            # Have to have this up here in case there was a perfect match
92
+            if current_money >= goal:
93
+                break;
94
+
95
+            for y in range(0, len(data) - panel):
96
+                additional_amt = data[y][1] * person['yield'] - replace_cost
97
+                if current_money + additional_amt >= goal:
98
+                    current_money += additional_amt
99
+                    person['panels'].append((data[y][0], data[y][1]))
100
+                    break;
101
+
102
+    if current_money >= goal:
103
+        break;
104
+
105
+# Print the output, all pretty like
106
+for person in people:
107
+    print ' '.join([person['name'], '=', repr(person['panels'])])
108
+
109
+# Add up how much money is left
110
+money_left = 0
111
+for x in range(panel, len(data)):
112
+    money_left += data[x][1]
113
+
114
+# Print out how much money is left
115
+locale.setlocale(locale.LC_ALL, '')
116
+print 'Total cash left in bannana stand: $' + format(money_left, "n")

+ 101 - 0
sample.txt

@@ -0,0 +1,101 @@
1
+50
2
+9792
3
+19569
4
+13013
5
+10983
6
+11110
7
+15063
8
+7362
9
+18062
10
+15531
11
+24008
12
+12426
13
+17110
14
+15920
15
+20944
16
+14871
17
+14719
18
+12762
19
+9705
20
+24858
21
+14337
22
+21046
23
+9717
24
+18501
25
+16823
26
+5947
27
+11910
28
+16470
29
+23803
30
+16542
31
+19287
32
+11654
33
+14350
34
+12255
35
+19726
36
+20944
37
+14854
38
+22051
39
+24780
40
+19347
41
+6784
42
+19151
43
+18677
44
+8326
45
+19213
46
+5273
47
+19203
48
+17744
49
+23050
50
+13788
51
+19397
52
+9353
53
+11906
54
+18400
55
+18435
56
+24011
57
+12917
58
+9279
59
+10382
60
+21076
61
+22183
62
+10047
63
+18996
64
+15770
65
+16315
66
+13896
67
+24358
68
+21411
69
+12523
70
+21009
71
+9518
72
+6257
73
+16728
74
+11328
75
+6481
76
+10491
77
+8025
78
+15267
79
+15139
80
+5906
81
+9159
82
+6096
83
+7502
84
+12151
85
+13631
86
+20608
87
+19340
88
+24533
89
+8645
90
+16090
91
+8457
92
+24081
93
+23193
94
+19051
95
+24218
96
+16098
97
+9827
98
+14198
99
+14555
100
+21891
101
+10445