Analysis And Algorithms CMSC 201 Search Sometimes we

  • Slides: 25
Download presentation
Analysis And Algorithms CMSC 201

Analysis And Algorithms CMSC 201

Search Sometimes, we use the location of a piece of information in a list

Search Sometimes, we use the location of a piece of information in a list to store information. If I have the list [4, 5, 2, 3], there may (should) be some significance to this order. That means sometimes we want to find where in the list something is!

Exercise Write a function that takes a list and a variable and finds and

Exercise Write a function that takes a list and a variable and finds and returns the first location of the variable in the list. def find(my. List, my. Var):

Exercise Write a function that takes a list and a variable and finds and

Exercise Write a function that takes a list and a variable and finds and returns the first location of the variable in the list. If it’s not found, return -1. def find(my. List, my. Var): for iin range(0, len(my. List)): if my. List[i] == my. Var: return i return -1

Search This is called linear search! It’s a fairly common, if simple operation. Now,

Search This is called linear search! It’s a fairly common, if simple operation. Now, imagine we’re looking for information in something sorted, like a phone book. We know someone’s name, and want to find their entry in the book (just like we knew the variable we were trying to locate in the search above). What is a good algorithm for locating their phone number? Think about how you would do this.

Search Algorithm in English: Open the book midway through. If the person’s name is

Search Algorithm in English: Open the book midway through. If the person’s name is on the page you opened to, you’re done! If the person’s name is after the page you opened to, tear the book in half, throw the first half away and repeat this process on the second half. If the person’s name is before the page you opened to, tear the book in half, throw the second half away and repeat this process on the first half.

Search Open the book midway through. If the person’s name is on the page

Search Open the book midway through. If the person’s name is on the page you opened to, you’re done! If the person’s name is after the page you opened to, tear the book in half, throw the first half away and repeat this process on the second half. If the person’s name is before the page you opened to, tear the book in half, throw the second half away and repeat this process on the first half. This is very hard on phone books, but you’ll find the name!

Search We can use the same idea for searching sorted lists! To make our

Search We can use the same idea for searching sorted lists! To make our problem slightly easier, let’s make it the problem of “checking to see if something is in a sorted list”. For purposes of our example, if there’s no “middle” of the list, we’ll just look at the lower of the two possible indices. So if the list has 11 elements, the fifth one would be our middle.

Search Say we’re looking for 21. Here’s the list: [1, 4, 5, 7, 10,

Search Say we’re looking for 21. Here’s the list: [1, 4, 5, 7, 10, 14, 18, 21, 22, 23, 28] 14 is our middle! 21 is greater than 14, so we’ll look at the right half of the list. [18, 21, 22, 23, 28] Our middle is now 22, so we’ll only look at the left half of the list. [18, 21] And we’ve found it!

Search This algorithm is called binary search. Binary search is a problem that can

Search This algorithm is called binary search. Binary search is a problem that can be broken down into something simple (breaking a list in half) and a smaller version of the original problem (searching that half of the list). That means we can use recursion!

Exercise Write a recursive binary search! Remember to ask yourself: What is our base

Exercise Write a recursive binary search! Remember to ask yourself: What is our base cases? What is the recursive step? def binary. Search(my. List, item): A hint: in order to get the number at the middle of the list, use this line: my. List[len(my. List) // 2] Anyone remember what the // 2 does?

Exercise Write a recursive binary search! def binary. Search(my. List, item): if(len(my. List) ==

Exercise Write a recursive binary search! def binary. Search(my. List, item): if(len(my. List) == 0): return False middle = len(my. List)//2 if(my. List[middle] == item): return True elif(my. List[middle] < item): return binary. Search(my. List[middle+1: ], item) else: return binary. Search(my. List[: middle], item)

Compare! Say we have a list that does not contain what we’re looking for.

Compare! Say we have a list that does not contain what we’re looking for. How many things in the list does linear search have to look at for it to figure out the item’s not there for a list of 8 things? 16 things? 32 things? How about binary search looking through a list of 8, 16, and 32 things? Notice anything different?

Compare! These algorithms scale differently! Linear search does work equal to the number of

Compare! These algorithms scale differently! Linear search does work equal to the number of items in the list while binary search does work equal to the log 2 of the numbers in the list! (Remember, a log 2(x) is basically asking “ 2 to what power equals x? ” This is basically the same as saying “how many times can I divide x in half before I hit 1? ” Which should make sense in this context. )

Compare! This means as our lists gets bigger, linear search becomes worse way faster

Compare! This means as our lists gets bigger, linear search becomes worse way faster than binary search.

Another Example Consider another example. Say we have a list, and we want find

Another Example Consider another example. Say we have a list, and we want find the sum of everything in that list multiplied by everything else in that list (this is a completely arbitrary example). So if the list is [1, 2, 3], we want to find the value of: 1*1 + 1*2 + 1*3 + 2*1 + 2*2 + 2*3 + 3*1 + 3*2 + 3*3 As an exercise, try writing this function! def sum. Of. All. Products(my. List):

Another Example def sum. Of. All. Products(my. List): result = 0 for item in

Another Example def sum. Of. All. Products(my. List): result = 0 for item in my. List: for item 2 in my. List: result += item * item 2 return result

Another Example Now the big question: How many multiplications does this have to do

Another Example Now the big question: How many multiplications does this have to do for a list of 8 things? 16 things? 32 things?

Another Example For 8 things, it does 64 multiplications. For 16 things, it does

Another Example For 8 things, it does 64 multiplications. For 16 things, it does 256 multiplications. For 32 things, you do 1024 multiplications. In general, if you give it a list of size N, you’ll have to do N 2 multiplications!

Formalizing For a list of size N, linear search does N operations. So we

Formalizing For a list of size N, linear search does N operations. So we say it is O(N) (pronounced “oh of n”). For a list of size N, binary search does lg(N) operations, so we say it is O(lg(N)) For a list of size N, our sum of products function does N 2 operations, which means it is O(N 2). The function in the parentheses indicates how fast the algorithm scales.

Exercise Sort from best to worst! O(N 3) O(lg(N)) O(1) O(N 2) O(N!)

Exercise Sort from best to worst! O(N 3) O(lg(N)) O(1) O(N 2) O(N!)

Exercise What is the big O of the following, given a list of size

Exercise What is the big O of the following, given a list of size N: for i in my. List: for j in my. List: for k in my. List: foo()

Exercise What is the big O of the following, given a list of size

Exercise What is the big O of the following, given a list of size N: for i in my. List: for j in my. List: for k in my. List: foo() This will be O(N 3)

Exercise What about this? for i in my. List: for j in my. List:

Exercise What about this? for i in my. List: for j in my. List: for k in my. List: foo() for i in my. List: foo()

Exercise For a list of size 5, the first loop will be 125 and

Exercise For a list of size 5, the first loop will be 125 and the second loop will be 5, so it will execute 130 times. List of size 10: 1000 + 10 List of size 100: 1000000 + 100 As you can see, the second part of the code isn’t having much of an effect on the overall number of operations. This code snippet would be O(N 3+N). However, as N approaches infinity, the smaller terms stop mattering. So we would drop the N and simply call this O(N 3)