Implementing a Python-ish language is easy enough. Depending on your definition, Lua already is one. Implementing the totality of Python is very hard to do performantly. Anything you think you can cache can probably have that cache violated, and real code will tend to do it. For instance, surely you can just cache a class -> method table once? My goodness, no. The class can be dynamically modified, including rewriting what methods exist. This happens in, for instance, interpreter reloads, so it's a real problem. An instance can have a method dynamically overloaded. (Prototype inheritance is not supported by the language's style or keywords, but it is essentially supported by the semantic model.) Heck, an instance probably isn't what you think it is, check this out (tested in Python 2.7.4 and 3.3.1):
>>> class A:
... def method(self):
... print("A")
...
>>> class B:
... def method(self):
... print ("B")
...
>>> a = A()
>>> a.__class__
<class '__main__.A'>
>>> a.__class__ = B
>>> a.method()
B
"Aaaaaaaaa!" goes the interpreter implementor.
It's not the raw syntax that is hard, it's the mutability of everything, you know, a user gets an instance of something, adds an overload of the __add__ operator to just that instance which then proceeds to change the class of the other element of the addition operation... sure, it doesn't happen often but it happens often enough you can't just ignore it, unfortunately, or what you've implemented isn't Python anymore.
I'm convinced that this is a hard task, hard enough that probably no one will do it properly. But for emulating Python class semantics, is there any reason why we can't:
1. Come up with an inefficient but exact modelling of the semantics in pure Lua using tables and metamethods. I think I can write metamethods showing exactly the behaviour you describe.
2.Come up with an efficient implementation of python_class userdata?
The problem you describe is the problem of really understanding what's going on, not a deficit in Lua's ability to model it.
It's not the raw syntax that is hard, it's the mutability of everything, you know, a user gets an instance of something, adds an overload of the __add__ operator to just that instance which then proceeds to change the class of the other element of the addition operation... sure, it doesn't happen often but it happens often enough you can't just ignore it, unfortunately, or what you've implemented isn't Python anymore.