Refreshing an Excel File using Python 3 - python-3.x

I am new to Python and I am trying to write a function to refresh the contents of excel files using the following code:
# function that refreshes files
def refresh_file(file_to_refresh):
excel = win32com.client.Dispatch("Excel.Application")
excel.Visible = False
workbook = excel.Workbooks.Open(file_to_refresh)
workbook.RefreshAll()
workbook.Save()
excel.Quit()
refresh_file('C:\\Users\\michaelw\\Desktop\\Team Allocations\\Client Care - Liaison_dev.xlsx')
refresh_file('C:\\Users\\michaelw\\Desktop\\Team Allocations\\Client Care - ROR_dev.xlsx')
It works perfectly fine when when I call the function for the Client Care - Liaison_dev.xlsx file however when I call another excel file to refresh afterwards (Such as the Client Care - ROR_dev.xlsx ) I get the following error:
Traceback (most recent call last):
File "c:\Users\michaelw\Desktop\Team Allocations\Team_allocation.py", line 189, in <module>
refresh_file('C:\\Users\\michaelw\\Desktop\\Team Allocations\\Client Care - ROR_dev.xlsx')
File "c:\Users\michaelw\Desktop\Team Allocations\Team_allocation.py", line 120, in refresh_file
workbook = excel.Workbooks.Open(file_to_refresh)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "C:\Users\michaelw\AppData\Local\Temp\gen_py\3.11\00020813-0000-0000-C000-000000000046x0x1x9\Workbooks.py", line 75, in Open
ret = self._oleobj_.InvokeTypes(1923, LCID, 1, (13, 0), ((8, 1), (12, 17), (12, 17), (12, 17), (12, 17), (12, 17), (12, 17), (12, 17), (12, 17), (12, 17), (12, 17), (12, 17), (12, 17), (12, 17), (12, 17)),Filename
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
pywintypes.com_error: (-2147352567, 'Exception occurred.', (0, 'Microsoft Excel', 'Open method of Workbooks class failed', 'xlmain11.chm', 0, -2146827284), None)

Related

Removing duplicate elements in a list with sets of arrays in python

I have a list[(position,id)] from the user based on the ids it chooses which I collect in data
data[(position,id)] = [(1,0),(2,0),(7,3),(8,6),(3,11),(3,11),(4,0),(5,1),(5,1),(6,2),(9,5),(10,7),(15,0),(16,10),(11,0),(11,1),(12,15),(13,8),(13,8),(13,9),(14,9)]
There are some duplicate elements in the list which I sorted out using *set(list) command
listdata = data
res=[]
res = [*set(listdata)]
print(res)
I get the res list as follows:
output: res = [(11, 1), (13, 8), (6, 2), (4, 0), (16, 10), (11, 0), (2, 0), (5, 1), (10, 7), (7, 3), (9, 5), (15, 0), (13, 9), (14, 9), (8, 6), (12, 15), (1, 0), (3, 11)]
But what I want is only 16 elements in the list on first come basis with positions 1 to 16, if you see here I have got 2 entries with position 11 [(11,1),(11,0)] and position 13[(13,8),(13,9)]
Required output:
res=[(11, 1), (13, 8), (6, 2), (4, 0), (16, 10), (2, 0), (5, 1), (10, 7), (7, 3), (9, 5), (15, 0), (14, 9), (8, 6), (12, 15), (1, 0), (3, 11)]
Can anyone suggest alternate solution?
This should probably be done with a generator.
res = [(11, 1), (13, 8), (6, 2), (4, 0), (16, 10), (11, 0), (2, 0), (5, 1), (10, 7), (7, 3), (9, 5), (15, 0), (13, 9), (14, 9), (8, 6), (12, 15), (1, 0), (3, 11)]
def foo(_res, max_items):
keys = []
for k,v in _res:
if k not in keys:
yield (k,v)
keys.append(k)
if len(keys) > max_items:
return
print(list(foo(res, 16)))
output:
[(11, 1), (13, 8), (6, 2), (4, 0), (16, 10), (2, 0), (5, 1), (10, 7), (7, 3), (9, 5), (15, 0), (14, 9), (8, 6), (12, 15), (1, 0), (3, 11)]
you can use a map to record every position only once
data = [(1,0),(2,0),(7,3),(8,6),(3,11),(3,11),(4,0),(5,1),(5,1),(6,2),(9,5),(10,7),(15,0),(16,10),(11,0),(11,1),(12,15),(13,8),(13,8),(13,9),(14,9)]
bucket = {}
for d in data:
bucket[d[0]] = d[1]
print(list(bucket.items()))
output is:
[(1, 0), (2, 0), (7, 3), (8, 6), (3, 11), (4, 0), (5, 1), (6, 2), (9, 5), (10, 7), (15, 0), (16, 10), (11, 1), (12, 15), (13, 9), (14, 9)]
update:
I am sorry I missed the description: "But what I want is only 16 elements in the list on first come basis", my answer above keeps the later came value, if you want to keep the first came one, do something like this:
data = [(1,0),(2,0),(7,3),(8,6),(3,11),(3,11),(4,0),(5,1),(5,1),(6,2),(9,5),(10,7),(15,0),(16,10),(11,0),(11,1),(12,15),(13,8),(13,8),(13,9),(14,9)]
bucket = {}
for d in data:
if d[0] not in bucket:
# if you never seen it, keep it, else ingore it.
bucket[d[0]] = d[1]
print(list(bucket.items()))

How to change two-dimension label to one-dimension label?

I have a two-dimension (10,2) coordinate which indicates each points label, like
coord_list = [(19, 17), (19, 17), (5, 26), (19, 17), (5, 26), (5, 26), (15, 17), (19, 5), (18, 6), (5, 26)]
I want to change it to a label list that only have one dimension (10,1),(assign a "label" to every unique item and replace each item by its label),like
label_list = [1,1,0....2,3]
I just want to classified points that have same coordinate in a same label, is there some more simple way can achieve it?
I tried to use this code,
label_list = []
for idx, coord in enumerate(coord_list):
if coord == (19,17):
label = 1
label_list.append(label)
if ...
But the problem is I don't know how many different coordinate in my coord_list, so I cannot write all if sentence in my code
Here's what I think you're after. I convert the list to a set, which eliminates duplicates. Then back to a list, and I sort it. Then I map each element of the original list to its index in that sorted list. There are only 5 unique points here, so the indexes will be from 0 to 4:
coord_list = [(19, 17), (19, 17), (5, 26), (19, 17), (5, 26), (5, 26), (15, 17), (19, 5), (18, 6), (5, 26)]
a = sorted(list(set(coord_list)))
print(a)
b = [a.index(i) for i in coord_list]
print(b)
Output:
[(5, 26), (15, 17), (18, 6), (19, 5), (19, 17)]
[4, 4, 0, 4, 0, 0, 1, 3, 2, 0]

Log plots in matplotlib is creating two lines

I was wondering why my loglog plots are creating two lines when it's just the orange one I want and why the labels won't show? Any insight would be greatly appreciated.
import matplotlib.pyplot as plt
data1 = [(3, 5034), (2, 4596), (4, 1469), (5, 1209), (6, 540), (7, 380), (8, 196), (9, 136), (10, 71), (11, 47), (12, 39), (13, 20), (14, 16), (15, 12), (16, 6), (18, 5), (17, 2), (19, 2), (22, 2), (1, 1), (24, 1), (20, 1)]
plt.loglog(data1, basex=2, basey=2, label='N1')
plt.show()

(Algorithms) Finding the shortest path that passes through a required set of nodes (possibly with BFS) and returns to the origin in Python

I am trying to find a shortest path that passes through a set of nodes [4,7,9] (order does not need to be preserved) and then returns to the origin (node 1). I have the set of edges:
E = [(1, 10), (1, 11), (2, 3), (2, 10), (3, 2), (3, 12), (4, 5), (4, 12), (5, 4), (5, 14), (6, 7), (6, 11), (7, 6), (7, 13), (8, 9), (8, 13), (9, 8), (9, 15), (10, 1), (10, 11), (10, 2), (11, 1), (11, 10), (11, 6), (12, 13), (12, 3), (12, 4), (13, 12), (13, 7), (13, 8), (14, 15), (14, 5), (15, 14), (15, 9)]
and I tried adapting the answer at How can I use BFS to get a path containing some given nodes in order? but yielded the error:
Traceback (most recent call last):
File "C:/Users/../rough-work.py", line 41, in <module>
graph[edge[0]].link(graph[edge[-1]])
KeyError: 15
My adapted code is as follows:
class Node:
def __init__(self, name):
self.name = name
self.neighbors = []
def link(self, node):
# The edge is undirected: implement it as two directed edges
self.neighbors.append(node)
node.neighbors.append(self)
def shortestPathTo(self, target):
# A BFS implementation which retains the paths
queue = [[self]]
visited = set()
while len(queue):
path = queue.pop(0) # Get next path from queue (FIFO)
node = path[-1] # Get last node in that path
for neighbor in node.neighbors:
if neighbor == target:
# Found the target node. Return the path to it
return path + [target]
# Avoid visiting a node that was already visited
if not neighbor in visited:
visited.add(neighbor)
queue.append(path + [neighbor])
###
n = 15
nodes = list(range(1,n))
E = [(1, 10), (1, 11), (2, 3), (2, 10), (3, 2), (3, 12), (4, 5), (4, 12), (5, 4), (5, 14), (6, 7), (6, 11), (7, 6), (7, 13), (8, 9), (8, 13), (9, 8), (9, 15), (10, 1), (10, 11), (10, 2), (11, 1), (11, 10), (11, 6), (12, 13), (12, 3), (12, 4), (13, 12), (13, 7), (13, 8), (14, 15), (14, 5), (15, 14), (15, 9)]
# Create the nodes of the graph (indexed by their names)
graph = {}
for letter in nodes:
graph[letter] = Node(letter)
print(graph)
# Create the undirected edges
for edge in E:
graph[edge[0]].link(graph[edge[-1]])
# Concatenate the shortest paths between each of the required node pairs
start = 1
path = [graph[1]]
for end in [4,7,9,1]:
path.extend( graph[start].shortestPathTo(graph[end])[1:] )
start = end
# Print result: the names of the nodes on the path
print([node.name for node in path])
What could possibly be the problem with the code? I will like to extend the graph to a arbitrarily large number of nodes, greater than 26 - the number of alphabets (as I infer that the previous implementation was only for character-based nodes). Or, if there is a more straightforward way in doing this that will be great!
Thanks and some help will be deeply appreciated!
The KeyError: 15 and your line print(graph) should have given you the clue: the latter shows that your graph dictionary contains only 14 entries, whereas your edges in E clearly make reference to 15 separate indices.
Change n = 15 to n = 16 and it works:
[1, 10, 2, 3, 12, 4, 12, 13, 7, 13, 8, 9, 8, 13, 7, 6, 11, 1]
Remember that:
>>> len(list(range(1,16)))
15

python sqlite3 List

I have a question about sqlite3 in python, it is about the list problem.
Here is the question:
Write a function getMay(dbName) that takes as a parameter the filename of above database and returns two lists, one with the days and one with the temperatures at noon on those days.
Here is My code:
import sqlite3
def getMay(dbName):
conn = sqlite3.connect(dbName)
cur = conn.cursor()
cur.execute('select Day,Temp from May14 where Time= "12:00" order by Day ASC')
print(cur.fetchall())
cur.close()
conn.close()
Here is my output:
[(1, 13.7), (2, 11.1), (3, 12.2), (4, 13.2), (5, 12.9), (6, 12.5), (7,
9.6), (8, 11.6), (9, 13.2), (10, 19.2), (11, 21.7), (12, 15.2), (13, 11.9), (14, 16.4), (15, 12.2), (16, 10.1), (17, 9.8), (18, 16.2), (19, 21.5), (20, 17.8), (21, 17.0), (22, 18.6), (23, 16.5), (24, 21.2), (25, 25.4), (26, 27.8), (27, 27.3), (28, 13.7), (29, 15.0), (30,
22.5), (31, 21.0)]
But the correct output should look like:
([1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20,
21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31], [13.7, 11.1, 12.2, 13.2,
12.9, 12.5, 9.6, 11.6, 13.2, 19.2, 21.7, 15.2, 11.9, 16.4, 12.2, 10.1,
9.8, 16.2, 21.5, 17.8, 17.0, 18.6, 16.5, 21.2, 25.4, 27.8, 27.3, 13.7,
15.0, 22.5, 21.0])
Anyone know how to solve this problem?
Please help! Thank!
one easy solution could be this:
dayTemp_list = [(1, 13.7), (2, 11.1), (3, 12.2), (4, 13.2), (5, 12.9), (6, 12.5), (7, 9.6), (8, 11.6), (9, 13.2), (10, 19.2), (11, 21.7), (12, 15.2), (13, 11.9), (14, 16.4), (15, 12.2), (16, 10.1), (17, 9.8), (18, 16.2), (19, 21.5), (20, 17.8), (21, 17.0), (22, 18.6), (23, 16.5), (24, 21.2), (25, 25.4), (26, 27.8), (27, 27.3), (28, 13.7), (29, 15.0), (30, 22.5), (31, 21.0)]
days = []
temp = []
for i in dayTemp_list:
days.append(i[0])
temp.append(i[1])
result = (days,temp)
print result

Resources