Minimax: how can I implement it in Python? - python

As long as I've been a programmer I still have a very elementary level education in algorithms (because I'm self-taught). Perhaps there is a good beginner book on them that you could suggest in your answer.

As a general note, Introduction to Algorithms. That book will get you through pretty much everything you need to know about general algorithms.
Edit:
As AndrewF mentioned, it doesn't actually contain minimax specifically, but it's still a very good resource for learning to understand and implement algorithms.

Look at the wikipedia article on Negamax: http://en.wikipedia.org/wiki/Negamax. It's a slight simplification of minimax that's easier to implement. There's pseudocode on that page.

There is an implementation of minimax as part of an othello game here (and for browsers here).
Stepping through this with a debugger and/or through use of logging statements
may supplement theoretical descriptions of the algorithm.
This visualization applet may also help.
At each stage the player will choose the move which is best for himself. What's best for one player will be worst for the other player. So at one stage the game state with the minimum score will be chosen, and at the next stage the game state available with the maximum score will be chosen, etc.

Related

How to use python when learning algorithms?

Basically, I am trying to learn some very basic data structures and algorithms using python. However I think when trying to implementing these algorithms, I unknowingly start using python tricks a bit, even as simple as the following which will not be considered tricks by any stretch of imagination
for i, item in enumerate(arr):
# Algo implementation
or
if item in items:
# do something
I don't know what is the general guideline to follow so that I can grasp the algorithm as it's meant to implemented.
It is all right to use Python's techniques to solve problems. The main exception is when Python does something for you and you want to learn how that something was done. One example is Python's heapq--You can't use that directly if your purpose is to understand how the binary heap structure can be used to implement a priority queue. Of course, you could read the source code and learn much that way.
One thing that can help you is to read a data structures and algorithms book that is based on Python. Then you can be assured that Python will not be used to slide over important topics--at least, if the book is any good.
One such book is Problem Solving with Algorithms and Data Structures. Another is Classic Computer Science Problems in Python. The first book is a free PDF download, though I believe there is a more recent edition that is not free. The second is not free but you can get a discount of 40% at the publisher's web site if you use a discount code mentioned in the Talk Python to Me podcast. I am working through the latter book now, as a reminder of the class I took a very long time ago.
As to a recommendation, the price may be a deciding factor for you. The emphases of the two books also differs. The first is older, using more generic Python and not using many of Python's special features. It is also closer to a textbook, going more into depth in its topics. It covers things like execution complexity, for example. The PDF version, however, does not cover as many topics as other versions I have seen. The PDF does not cover graphs (networks), for example, which another version (which I cannot find now) does.
The second is much more recent, using features of Python 3.7 such as type hints. It also is more of an introduction or review. I think I can use "fair use" to quote the relevant section of the book:
Who is this book for?
This book is for both intermediate and experienced programmers.
Experienced programmers who want to deepen their knowledge of Python
will find comfortably familiar problems from their computer science or
programming education. Intermediate programmers will be introduced to
these classic problems in the language of their choice: Python.
Developers getting ready for coding interviews will likely find this
book to be valuable preparation material.
In addition to professional programmers, students enrolled in
undergraduate computer science programs who have an interest in Python
will likely find this book helpful. It makes no attempt to be a
rigorous introduction to data structures and algorithms. This is not a
data structures and algorithms textbook. You will not find proofs or
extensive use of big-O notation within its pages. Instead, it is
positioned as an approachable, hands-on tutorial to the
problem-solving techniques that should be the end product of taking
data structure, algorithm, and artificial intelligence classes.
Once again, knowledge of Python’s syntax and semantics is assumed. A
reader with zero programming experience will get little out of this
book, and a programmer with zero Python experience will almost
certainly struggle. In other words, Classic Computer Science Problems
in Python is a book for working Python programmers and computer
science students.
If you want to understand how an algorithm works, I would strongly recommend to work with flowcharts. They represent the algorithmic procedure as relations between the elementary logical statements the algorithm is made of and are independent on the programming language an algorithm might be implemented.
If you want to learn python along with it, then here is what you can do:
1. Study the flowchart of the algorithm that interests you.
2. Translate that flowchart 1-to-1 into python code.
3. Have a closer look at your python code and try to optimize or compact it.
This can be best illustrated with an example:
1.
Here is the flowchart of Euclid's algorithm that finds the greatest common denominator of two numbers (taken form the wiki page Algorithm):
To understand an algorithm means to be able to follow or even reproduce this flowchart
2.
Now if your goal is to learn python a great exercise is to take a flowchart and translate it to python. No shortcuts, no simplifications, just 1-to-1 as it is written, translate the algorithm to python. You won't be fooled by any tricks or masked complexity when doing so, as the flowchart tells you the elementary logical steps and you are just translating them to your preferred programming language.
For the example above, a crude 1-to-1 implementation looks like this:
def gcd(a,b): # point 1
while True:
if b == 0: # p. 2
return a # p. 8 + 9
if a > b: # p. 3
a = a - b # p. 6
# p. 7
else: # p. 3
b = b - a # p. 4
# p. 5
3.
By now you have both learned how the algorithm works and how you implement logical statements in python. The tricks you mentioned earlier can enter the game here. You can start to play around and try to make the implementation more efficient, more compact or a one-liner (people like this for some reason). This will not only help your logical understanding but it will also deepen your knowledge of the programming language you are using.
As for the example at hand, Euclid's algorithm, there is not a lot of fancy business that comes to my mind. I somehow find recursive calls elegant, so here is a tricky implementation using this:
def gcd(a,b):
if b == 0:
return a
else:
return gcd(a-b,b) if a > b else gcd(a, b - a)
Note the you can (and sometimes even have to) do this procedure in the reverse order. It can happen that the only thing you know about an algorithm is an implementation of it. The you would proceed exactly in the reversed order: 3.->2. Try to identify and 'expand' all trickery that might be present in the implementation. 2.->1. Use the 'expanded' implementation to create a flowchart of the algorithm, in order to have a proper definition.
They are not tricks!
These are the same thing you would do in any other language. It's just made more simpler in python.
In c/c++ you would do,
for(int i=0; i<sizeof(arr)/sizeof(arr[0]); i++) {
// access the array elements here as arr[i]
}
The same thing you would do in python in a bit convenient way i.e.
for i, a in enumerate (arr):
# do something
or
for i in range(len(arr)):
# do something with arr elements
Your algorithms will NOT depend upon these syntactical difference.
Whether it is in python or in c/c++ or in any other language, if you have a good understanding of the language, you are good to go with any thing. You just have to keep in mind the time complexities of the algorithms you use and how you implement them.
The thing with python is that it's way more easy to understand, it's shorter to write, has a lot of inbuilt functions, you need no class or a main function to execute your program and many more.
If you ask me, I would not say they are any tricks. All programming languages have these things in common with just syntactical difference.
It depends on what you are trying to implement. Like say if you are trying to implement linked list, you just need to know what can you use in python to implement that.

Efficient scheduling of university courses

I'm currently working on a website that will allow students from my university to automatically generate valid schedules based on the courses they'd like to take.
Before working on the site itself, I decided to tackle the issue of how to schedule the courses efficiently.
A few clarifications:
Each course at our university (and I assume at every other
university) comprises of one or more sections. So, for instance,
Calculus I currently has 4 sections available. This means that, depending on the amount of sections, and whether or not the course has a lab, this drastically affects the scheduling process.
Courses at our university are represented using a combination of subject abbreviation and course code. In the case of Calculus I: MATH 1110.
The CRN is a code unique to a section.
The university I study at is not mixed, meaning males and females study in (almost) separate campuses. What I mean by almost is that the campus is divided into two.
The datetimes and timeranges dicts are meant to decreases calls to datetime.datetime.strptime(), which was a real bottleneck.
My first attempt consisted of the algorithm looping continuously until 30 schedules were found. Schedules were created by randomly choosing a section from one of the inputted courses, and then trying to place sections from the remaining courses to try to construct a valid schedule. If not all of the courses fit into the schedule i.e. there were conflicts, the schedule was scrapped and the loop continued.
Clearly, the above solution is flawed. The algorithm took too long to run, and relied too much on randomness.
The second algorithm does the exact opposite of the old one. First, it generates a collection of all possible schedule combinations using itertools.product(). It then iterates through the schedules, crossing off any that are invalid. To ensure assorted sections, the schedule combinations are shuffled (random.shuffle()) before being validated. Again, there is a bit of randomness involved.
After a bit of optimization, I was able to get the scheduler to run in under 1 second for an average schedule consisting of 5 courses. That's great, but the problem begins once you start adding more courses.
To give you an idea, when I provide a certain set of inputs, the amount of combinations possible is so large that itertools.product() does not terminate in a reasonable amount of time, and eats up 1GB of RAM in the process.
Obviously, if I'm going to make this a service, I'm going to need a faster and more efficient algorithm. Two that have popped up online and in IRC: dynamic programming and genetic algorithms.
Dynamic programming cannot be applied to this problem because, if I understand the concept correctly, it involves breaking up the problem into smaller pieces, solving these pieces individually, and then bringing the solutions of these pieces together to form a complete solution. As far as I can see, this does not apply here.
As for genetic algorithms, I do not understand them much, and cannot even begin to fathom how to apply one in such a situation. I also understand that a GA would be more efficient for an extremely large problem space, and this is not that large.
What alternatives do I have? Is there a relatively understandable approach I can take to solve this problem? Or should I just stick to what I have and hope that not many people decide to take 8 courses next semester?
I'm not a great writer, so I'm sorry for any ambiguities in the question. Please feel free to ask for clarification and I'll try my best to help.
Here is the code in its entirety.
http://bpaste.net/show/ZY36uvAgcb1ujjUGKA1d/
Note: Sorry for using a misleading tag (scheduling).
Scheduling is a very famous constraint satisfaction problem that is generally NP-Complete. A lot of work has been done on the subject, even in the same context as you: Solving the University Class Scheduling Problem Using Advanced ILP Techniques. There are even textbooks on the subject.
People have taken many approaches, including:
Dynamic programming
Genetic algorithms
Neural networks
You need to reduce your problem-space and complexity. Make as many assumptions as possible (max amount of classes, block based timing, ect). There is no silver bullet for this problem but it should be possible to find a near-optimal solution.
Some semi-recent publications:
QUICK scheduler a time-saving tool for scheduling class sections
Scheduling classes on a College Campus
Did you ever read anything about genetic programming? The idea behind it is that you let the 'thing' you want solved evolve, just by itsself, until it has grown to the best solution(s) possible.
You generate a thousand schedules, of which usually zero are anywhere in the right direction of being valid. Next, you change 'some' courses, randomly. From these new schedules you select some of the best, based on ratings you give according to the 'goodness' of the schedule. Next, you let them reproduce, by combining some of the courses on both schedules. You end up with a thousand new schedules, but all of them a tiny fraction better than the ones you had. Let it repeat until you are satisfied, and select the schedule with the highest rating from the last thousand you generated.
There is randomness involved, I admit, but the schedules keep getting better, no matter how long you let the algorithm run. Just like real life and organisms there is survival of the fittest, and it is possible to view the different general 'threads' of the same kind of schedule, that is about as good as another one generated. Two very different schedules can finally 'battle' it out by cross breeding.
A project involving school schedules and genetic programming:
http://www.codeproject.com/Articles/23111/Making-a-Class-Schedule-Using-a-Genetic-Algorithm
I think they explain pretty well what you need.
My final note: I think this is a very interesting project. It is quite difficult to make, but once done it is just great to see your solution evolve, just like real life. Good luck!
The way you're currently generating combinations of sections is probably throwing up huge numbers of combinations that are excluded by conflicts between more than one course. I think you could reduce the number of combinations that you need to deal with by generating the product of the sections for only two courses first. Eliminate the conflicts from that set, then introduce the sections for a third course. Eliminate again, then introduce a fourth, and so on. This should see a more linear growth in the processing time required as the number of courses selected increases.
This is a hard problem. It you google something like 'course scheduling problem paper' you will find a lot of references. Genetic algorithm - no, dynamic programming - yes. GAs are much harder to understand and implement than standard DP algos. Usually people who use GAs out of the box, don't understand standard techniques. Do some research and you will find different algorithms. You might be able to find some implementations. Coming up with your own algorithm is way, way harder than putting some effort into understanding DP.
The problem you're describing is a Constraint Satisfaction Problem. My approach would be the following:
Check if there's any uncompatibilities between courses, if yes, record them as constraints or arcs
While not solution is found:
Select the course with less constrains (that is, has less uncompatibilities with other courses)
Run the AC-3 algorithm to reduce search space
I've tried this approach with sudoku solving and it worked (solved the hardest sudoku in the world in less than 10 seconds)

how to build game playing neural network in Python?

I am a neural-network beginner. I'd like to learn the basics of neural networks by teaching computers to play checkers. Actually, the games I want to learn are Domineering and Hex.
These games are pretty easy to store and the rules are much simpler than chess, but there aren't too many people who play. If I can get this idea off the ground it would be great for experimenting Combinatorial Game Theory.
PyBrain seems to be the clear winner for Python neural networks, but who can walk me through how to set up a neural net for my game-playing task? A google search turned up Blondie24 in 2001 but it uses some genetic algorithms - I don't want to complicate things.
Once you replace "neural networks" by machine learning (or even artificial intelligence, rather, imho) as the comments rightly suggest, I think you're better off starting with Alpha-beta pruning, the Minimax algorithm, and Branch and bound ideas.
Basically :
At each step, you build the tree of all possible futures, and evaluate leaf positions with an evaluation function (e.g. board domination, connectivity, material, etc.)
Propagate the results up in the tree, choosing the best play you can make, and the worse your opponent can (the best for him), until you know what move to play in the position you're at.
Rinse, repeat. Branch and bound saves you a lot of computation if you have a few good heuristics, and the level of your programm will basically be how deep it'll be able to search the game tree.
This will most probably be the basic framework in which anyone would introduce new ideas, so if you're not familiar with it, go for it :-)

Code bacteria: evolving mathematical behavior

It would not be my intention to put a link on my blog, but I don't have any other method to clarify what I really mean. The article is quite long, and it's in three parts (1,2,3), but if you are curious, it's worth the reading.
A long time ago (5 years, at least) I programmed a python program which generated "mathematical bacteria". These bacteria are python objects with a simple opcode-based genetic code. You can feed them with a number and they return a number, according to the execution of their code. I generate their genetic codes at random, and apply an environmental selection to those objects producing a result similar to a predefined expected value. Then I let them duplicate, introduce mutations, and evolve them. The result is quite interesting, as their genetic code basically learns how to solve simple equations, even for values different for the training dataset.
Now, this thing is just a toy. I had time to waste and I wanted to satisfy my curiosity.
however, I assume that something, in terms of research, has been made... I am reinventing the wheel here, I hope. Are you aware of more serious attempts at creating in-silico bacteria like the one I programmed?
Please note that this is not really "genetic algorithms". Genetic algorithms is when you use evolution/selection to improve a vector of parameters against a given scoring function. This is kind of different. I optimize the code, not the parameters, against a given scoring function.
If you are optimising the code, perhaps you are engaged in genetic programming?
The free utility Eureqa is similar in the sense that in can create fitting symbolic functions (much more complicated than simple linear regression, etc.) based on multivariate input data. But, it uses GA to come up with the functions, so I'm not sure if that's exactly what you had in mind.
See also the "Download Your Own Robot Scientist" article on Wired for a breakdown of the general idea of how it works.
Nice article,
I would say you're talking about "gene expression programming" rather than "genetic programming", btw.
Are you familiar with Core Wars? I remember there were a number of code evolvers written for the game which had some success. For example, MicroGP++ is an assembly code generator that can be applied to the Core Wars assembly language (as well as to real problems!).

Python for mathematics students?

I need to deliver one and half hour seminar on programming for students at the department of mathematics.
I have chosen python as language.
What should be content of my presentation ?
What are good resources available ?
What is necessity of programming for maths students?
How will knowledge of programming will help them?
Thank you !!!
NOTE: I know here is one post but it doesn't solve my problem.
Do the getting started guide to scipy?
http://www.scipy.org/Getting_Started
Sage: http://www.sagemath.org/
Assuming that these students are new to programming (which is quite likely for math students), you'll want to give them a basic introduction to programming (what a function is, what a variable is, how each of these differ from functions and variables in math, etc).
Show them some example programs, with a view to things that will be helpful for math: numerical methods, matrix multiplication, etc.
Wherever possible, wow them so that they'll get excited about using computers for their own projects.
Some Python/Math resources
I would bring up using Python as a free & open source option to replace/augment expensive packages like Matlab, IDL, etc via:
scipy - fft's,
ipython - "shell"/debugger
matplotlib - 2d graphing
MayaVi - 3d graphing/visualization
This video may be helpful.
You are going to have to decide what you want to show them. If you want to show them how to using a computer can be a useful tool in mathematics show them sage and how you can perform numerical methods with it to get answers to hard questions. Then manipulate some algebraic formulas with it. Maybe show how it can whip through hard integrals and derivatives without sweating. They will be nearing the end of some of their first calulus courses after all.
None of this displays why they need to know how to program of course. This just shows how useful other people's programming is for them to use. While you do have the full power of python in sage the reality is the odd "for loop" and some "if statements" is really all of the programming most mathematicians will do with sage most of the time (though there is a significant minority who will do a lot more). If you want to go down this road I would suggest you try to get your hands on one of the Experimental mathematics books(http://www.experimentalmath.info/). These are the guys who (amongst many other interesting results) came up with BBP numbers: which is the way to find arbitrary digits of pi. They mostly use maple and mathematica but most of this work translates to sage.
I would strongly suggest you don't show them how to actually implement numerical methods themselves. Very few mathematicians are writing programs to solve numerical problems. Most just plug their programs into other people's programs. So I don't think showing how they could implement these methods themselves, if only they knew how to program, will excite anyone.
If this were me I think I would probably give a seminar building a simple game plugin for cgsuite (http://cgsuite.sourceforge.net/). I recognize that this is java and not python but their are a lot of advantages to this approach. First young mathematicians always get excited by combinatorial game theory. You are fundamentally showing them how they can use math to always win at certain games. It's like you are giving them a super power.
Second, you are implementing the rules of a game in a program. Game rules are great ways to learn programming idioms because they translate so directly into programming concepts.
And finally, you end up with a tool that can play your game perfectly. 90 minutes is a long time for a seminar as far as I'm concerned. If you can end on a bang, like with 10 minutes of playing a game against a computer, they will leave excited instead of bored and drained.
I would recommend solving a few different kinds of problems from Project Euler in Python and having a discussion about the solutions, how they could have been done differently to be more efficient, etc. as part of the seminar. Python is a very elegant language for solving mathematical problems and should be one of those easier understood than most by mathematics students, so I think you made a good choice there.
I'm assuming this is for Freshmen (only because most higher level Math students will likely know how to program)? If so, do something that is fun and relevant. Go through the basics, but maybe walk them through the logic / basic framework for a Game (which are heavily math oriented) or Python-Based Graphing Calculator.
If you want to get them real geeked though, show them Mathematica. I know, it's not what you selected ... but when I was a Sophomore Math major and first saw what you could do with it, I was in love.
Python will work well, but GNU Octave may be better.
What should be content of my presentation ?
The concept of functional programming with Python.
Some introduction to third party modules like NumPy and SciPy.
What are good resources available ?
Hans Petter Langtangen, Python Scripting for Computational Science, Springer
What is necessity of programming for maths students?
None. Usually maths students will have no problem in programming, since most programming language were developed to solve maths problem.
How will knowledge of programming will help them?
The computer was earlier developed as a tool for scientist to help them solve scientific/mathematics problems efficiently in a very short time, as compared to human.
http://www.sagemath.org
In our wiki is a collection of talks, they may help you! http://wiki.sagemath.org/Talks
Also be aware, that Sage contains NumPy, SciPy and SymPy. Therefore all information about these three python libraries hold for Sage.

Categories

Resources