kmp algorithm, very good