Fundamental techniques for designing effi cient algorithms and basic mathematical methods for analyzing their performance. Paradigms for algorithm design: divide-and-conquer, greedy methods, graph search techniques, dynamic programming. Design of effi cient data structures and analysis of the running time and space requirements of algorithms in the worst and average cases.