1. What is part of the final step when problem solving?
- Documentation
- Long-term remediation
- Finding the root cause
- Gathering information
2. Which tool can you use when debugging to look at library calls made by the software?
- top
- strace
- tcpdump
- ltrace
3. What is the first step of problem solving?
- Prevention
- Gathering information
- Long-term remediation
- Finding the root cause
4. What software tools are used to analyze network traffic to isolate problems? (Check all that apply)
- tcpdump
- wireshark
- strace
- top
5. The strace (in Linux) tool allows us to see all of the _____ our program has made.
- Network traffic
- Disk writes
- System calls
- Connection requests
6. When a user reports that an “application doesn’t work,” what is an appropriate follow-up question to gather more information about the problem?
- Is the server plugged in?
- Why do you need the application?
- Do you have a support ticket number?
- What should happen when you open the app?
7. What is a heisenbug?
- The observer effect.
- A test environment.
- The root cause.
- An event viewer.
8. The compare_strings function is supposed to compare just the alphanumeric content of two strings, ignoring upper vs lower case and punctuation. But something is not working. Fill in the code to try to find the problems, then fix the problems.
import re
def compare_strings(string1, string2):
#Convert both strings to lowercase
#and remove leading and trailing blanks
string1 = string1.lower().strip()
string2 = string2.lower().strip()
#Ignore punctuation
punctuation = r”[.?!,;:-‘]”
string1 = re.sub(punctuation, r””, string1)
string2 = re.sub(punctuation, r””, string2)
#DEBUG CODE GOES HERE
print(___)
return string1 == string2
print(compare_strings(“Have a Great Day!”, “Have a great day?”)) # True
print(compare_strings(“It’s raining again.”, “its raining, again”)) # True
print(compare_strings(“Learn to count: 1, 2, 3.”, “Learn to count: one, two, three.”)) # False
print(compare_strings(“They found some body.”, “They found somebody.”)) # False
- import re #to use regular expressions
def compare_strings(string1, string2): #function compare_strings that takes two strings as argument and compares them
string1 = string1.lower().strip() # converts the string1 characters to lowercase using lower() method and removes trailing blanks
string2 = string2.lower().strip() # converts the string1 characters to lowercase using lower() method and removes trailing blanks
punctuation = r”[-.?!,;:’]” #regular expression for punctuation characters
string1 = re.sub(punctuation, r””, string1) # specifies RE pattern i.e. punctuation in the 1st argument, new string r in 2nd argument, and a string to be handle i.e. string1 in the 3rd argument
string2 = re.sub(punctuation, r””, string2) # same as above statement but works on string2 as 3rd argument
print(‘string1:’,string1,’\nstring2:’,string2) #prints both the strings separated with a new line
return string1 == string2 # compares strings and returns true if they matched else false
#function calls to test the working of the above function compare_strings
print(compare_strings(“Have a Great Day!”,”Have a great day?”)) # True
print(compare_strings(“It’s raining again.”,”its raining, again”)) # True
print(compare_strings(“Learn to count: 1, 2, 3.”,”Learn to count: one, two, three.”)) # False
print(compare_strings(“They found some body.”,”They found somebody.”)) # False
9. How do we verify if a problem is still persisting or not?
- Restart the device or server hardware
- Attempt to trigger the problem again by following the steps of our reproduction case
- Repeatedly ask the user
- Check again later
10. The date time module supplies classes for manipulating dates and times, and contains many types, objects, and methods. You’ve seen some of them used in the dow function, which returns the day of the week for a specific date. We’ll use them again in the next_date function, which takes the date_string parameter in the format of “year-month-day”, and uses the add_year function to calculate the next year that this date will occur (it’s 4 years later for the 29th of February during Leap Year, and 1 year later for all other dates). Then it returns the value in the same format as it receives the date: “year-month-day”.
Can you find the error in the code? Is it in the next_date function or the add_year function? How can you determine if the add_year function returns what it’s supposed to? Add debug lines as necessary to find the problems, then fix the code to work as indicated above.
import datetime
from datetime import date
def add_year(date_obj):
try:
new_date_obj = date_obj.replace(year = date_obj.year + 1)
except ValueError:
# This gets executed when the above method fails,
# which means that we’re making a Leap Year calculation
new_date_obj = date_obj.replace(year = date_obj.year + 4)
return new_date_obj
def next_date(date_string):
# Convert the argument from string to date object
date_obj = datetime.datetime.strptime(date_string, r”%Y-%m-%d”)
next_date_obj = add_year(date_obj)
# Convert the datetime object to string,
# in the format of “yyyy-mm-dd”
next_date_string = next_date_obj.strftime(“yyyy-mm-dd”)
return next_date_string
today = date.today() # Get today’s date
print(next_date(str(today)))
# Should return a year from today, unless today is Leap Day
print(next_date(“2021-01-01”)) # Should return 2022-01-01
print(next_date(“2020-02-29”)) # Should return 2024-02-29
- import datetime
from datetime import date
def add_year(date_obj):
print(f”Original date: {date_obj}”)
try:
new_date_obj = date_obj.replace(year = date_obj.year + 1)
print(f”New date: {new_date_obj}”)
except ValueError:
# This gets executed when the above method fails,
# which means that we’re making a Leap Year calculation
new_date_obj = date_obj.replace(year = date_obj.year + 4)
print(f”New date: {new_date_obj} (leap year)”)
return new_date_obj
def next_date(date_string):
# Convert the argument from string to date object
date_obj = datetime.datetime.strptime(date_string, r”%Y-%m-%d”)
next_date_obj = add_year(date_obj)
# Convert the datetime object to string,
# in the format of “yyyy-mm-dd”
next_date_string = next_date_obj.strftime(“%Y-%m-%d”)
return next_date_string
today = date.today() # Get today’s date
print(next_date(str(today)))
# Should return a year from today, unless today is Leap Day
print(next_date(“2021-01-01”)) # Should return 2022-01-01
print(next_date(“2020-02-29”)) # Should return 2024-02-29
11. You have a list of computers that a script connects to in order to gather SNMP traffic and calculate an average for a set of metrics. The script is now failing, and you do not know which remote computer is the problem. How would you troubleshoot this issue using the bisecting methodology?
- Run the script with the first half of the computers.
- Run the script with last computer on the list.
- Run the script with first computer on the list
- Run the script with two-thirds of the computers.
12. The find_item function uses binary search to recursively locate an item in the list, returning True if found, False otherwise. Something is missing from this function. Can you spot what it is and fix it? Add debug lines where appropriate, to help narrow down the problem.
def find_item(list, item):
#Returns True if the item is in the list, False if not.
if len(list) == 0:
return False
#Is the item in the center of the list?
middle = len(list)//2
if list[middle] == item:
return True
#Is the item in the first half of the list?
if item < list[middle]:
#Call the function with the first half of the list
return find_item(list[:middle], item)
else:
#Call the function with the second half of the list
return find_item(list[middle+1:], item)
return False
#Do not edit below this line – This code helps check your work!
list_of_names = [“Parker”, “Drew”, “Cameron”, “Logan”, “Alex”, “Chris”, “Terry”, “Jamie”, “Jordan”, “Taylor”]
print(find_item(list_of_names, “Alex”)) # True
print(find_item(list_of_names, “Andrew”)) # False
print(find_item(list_of_names, “Drew”)) # True
print(find_item(list_of_names, “Jared”)) # False
- def find_item(list, item):
#Returns True if the item is in the list, False if not.
iflen(list) == 0:
returnFalse
# In order to use binary search, list needs to be sorted
list.sort()
#Is the item in the center of the list?
middle = len(list)//2
iflist[middle] == item:
returnTrue
#Is the item in the first half of the list?
if item < list[middle]:
#Call the function with the first half of the list
return find_item(list[:middle], item)
else:
#Call the function with the second half of the list
return find_item(list[middle+1:], item)
returnFalse
#Do not edit below this line – This code helps check your work!
list_of_names = [“Parker”, “Drew”, “Cameron”, “Logan”, “Alex”, “Chris”, “Terry”, “Jamie”, “Jordan”, “Taylor”]
print(find_item(list_of_names, “Alex”)) # True
print(find_item(list_of_names, “Andrew”)) # False
print(find_item(list_of_names, “Drew”)) # True
print(find_item(list_of_names, “Jared”)) # False
13. The binary_search function returns the position of key in the list if found, or -1 if not found. We want to make sure that it’s working correctly, so we need to place debugging lines to let us know each time that the list is cut in half, whether we’re on the left or the right. Nothing needs to be printed when the key has been located.
For example, binary_search([1, 2, 3, 4, 5, 6, 7, 8, 9, 10], 3) first determines that the key, 3, is in the left half of the list, and prints “Checking the left side”, then determines that it’s in the right half of the new list and prints “Checking the right side”, before returning the value of 2, which is the position of the key in the list.
Add commands to the code, to print out “Checking the left side” or “Checking the right side”, in the appropriate places.
def binary_search(list, key):
#Returns the position of key in the list if found, -1 otherwise.
#List must be sorted:
list.sort()
left = 0
right = len(list) – 1
while left <= right:
middle = (left + right) // 2
if list[middle] == key:
return middle
if list[middle] > key:
right = middle – 1
if list[middle] < key:
left = middle + 1
return -1
print(binary_search([10, 2, 9, 6, 7, 1, 5, 3, 4, 8], 1))
“””Should print 2 debug lines and the return value:
Checking the left side
Checking the left side
0
“””
print(binary_search([1, 2, 3, 4, 5, 6, 7, 8, 9, 10], 5))
“””Should print no debug lines, as it’s located immediately:
4
“””
print(binary_search([10, 9, 8, 7, 6, 5, 4, 3, 2, 1], 7))
“””Should print 3 debug lines and the return value:
Checking the right side
Checking the left side
Checking the right side
6
“””
print(binary_search([1, 3, 5, 7, 9, 10, 2, 4, 6, 8], 10))
“””Should print 3 debug lines and the return value:
Checking the right side
Checking the right side
Checking the right side
9
“””
print(binary_search([5, 1, 8, 2, 4, 10, 7, 6, 3, 9], 11))
“””Should print 4 debug lines and the “not found” value of -1:
Checking the right side
Checking the right side
Checking the right side
Checking the right side
-1
“””
- def binary_search(list, key):
#Returns the position of key in the list if found, -1 otherwise.
#List must be sorted:
list.sort()
left = 0
right = len(list) – 1
while left <= right:
middle = (left + right) // 2
iflist[middle] == key:
return middle
iflist[middle] > key:
print(“Checking the left side”)
right = middle – 1
iflist[middle] < key:
print(“Checking the right side”)
left = middle + 1
return-1
print(binary_search([10, 2, 9, 6, 7, 1, 5, 3, 4, 8], 1))
“””Should print 2 debug lines and the return value:
Checking the left side
Checking the left side
0
“””
print(binary_search([1, 2, 3, 4, 5, 6, 7, 8, 9, 10], 5))
“””Should print no debug lines, as it’s located immediately:
4
“””
print(binary_search([10, 9, 8, 7, 6, 5, 4, 3, 2, 1], 7))
“””Should print 3 debug lines and the return value:
Checking the right side
Checking the left side
Checking the right side
6
“””
print(binary_search([1, 3, 5, 7, 9, 10, 2, 4, 6, 8], 10))
“””Should print 3 debug lines and the return value:
Checking the right side
Checking the right side
Checking the right side
9
“””
print(binary_search([5, 1, 8, 2, 4, 10, 7, 6, 3, 9], 11))
“””Should print 4 debug lines and the “not found” value of -1:
Checking the right side
Checking the right side
Checking the right side
Checking the right side
-1
“””
14. When trying to find an error in a log file or output to the screen, what command can we use to review, say, the first 10 lines?
- wc
- tail
- head
- bisect