The problem is that you are matching the pattern [a, b]with the return value getArgs. If you run your program with something other than two arguments, then the return value will not match the pattern [a, b]. Therefore, if you do not run this program as
$ ./xie 1 2
command line arguments: ["1","2"]
He gives an error. Instead, if you wrote your code
main = do
args <- getArgs
case args of
[a, b] -> putStrLn $ "command line arguments: " ++ show [a, b]
_ -> putStrLn "Invalid number of arguments"
then you will never fail when matching with a pattern.