How to get a class object from class name - python

I want to get a class reference from class object in Python. Normally I use class name as a valid reference, but it does not always work.
Consider this code:
import inspect
import unittest
import pywin32_testutil
mro=inspect.getmro(pywin32_testutil.TestProgram)
mro[0]
> <class 'pywin32_testutil.TestProgram'>
mro[0].__module__ + '.' + mro[0].__name__
>'pywin32_testutil.TestProgram'
pywin32_testutil.TestProgram
> <class 'pywin32_testutil.TestProgram'>
From the object I'm able to determine class name and using class name I can get class object. However it does not always work. Continuing the example:
mro[1]
> <class 'unittest.main.TestProgram'>
mro[1].__module__ + '.' + mro[1].__name__
> 'unittest.main.TestProgram'
so far so good, however unittest.main.TestProgram reference is invalid:
unittest.main.TestProgram
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
AttributeError: type object 'TestProgram' has no attribute 'TestProgram'
How can I work around that?

Related

AttributeError with extended class in Python

I'm trying to create a new method for a class from a different file (not the file where the class was defined). My code is:
from derivations import derivation
class Derivation(derivation.Derivation):
def autoderive(self, index):
...
deriv = derivation.Derivation()
But if I try to run this method from the terminal, it doesn't work:
>>> deriv.autoderive()
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
AttributeError: 'Derivation' object has no attribute 'autoderive'
I don't have problems with the "native" methods. And I'm working with a fork of this: https://github.com/alexwarstadt/minimalism
Thank you very much.
I do not know much about the derivation module, but you are not creating an instance of your Derivation class, where you have defined the autoderive method, by doing this:
deriv = derivation.Derivation()
To create an instance of your custom class Derivation, that derives from derivation.Derivation():
deriv = Derivation()

Why can I not read the 'typename' after creating a namedtuple object in Python

This query is further with reference to this query
So, I am trying to execute the following code :
from collections import *
tp = namedtuple('emp', 'eid enames mob')
print(tp)
print(emp)
I can execute print(tp) and the output generated is <class '__main__.emp'>.
But when I try to execute print(emp), It generates the following exception :
Traceback (most recent call last):
File "a.py", line 5, in <module>
print(emp)
NameError: name 'emp' is not defined
What is the reason. The class emp is created. But I can not figure out how to access it directly. Or can I not ?
So basically, I can create instance of tp as tp() but not instances of emp in the same way. Why?
Option 1: Just repeat the type name when assigning to the returned type
tp = emp = namedtuple('emp', 'eid enames mob')
Option 2: Use a declarative style instead of the functional APIs
from typing import NamedTuple
class emp(NamedTuple):
eid: str
enames: str
mob: str

Splitting Lines in Python in a List?

I'm new-ish to Python and I'm having trouble achieving a result that I want. I'm opening a text file called urldata.txt which contains URLs that I need to break down by scheme, server, and path.
I have retrieved the data from the file:
urls = open("urldata.txt").read()
print(urls)
this returns:
http://www.google.com
https://twitter.com/search?q=%23ASUcis355
https://github.com/asu-cis-355/course-info
I want to break these URLs into 3 pieces each so that when I enter
urls.scheme()
urls.server()
urls.path()
It will return me the scheme of each URL when I enter
urls.scheme()
'http','https','https'
Then it will return the server when I enter
urls.server()
'google.com'
'twitter.com'
'github.com'
Finally, it will return the path when I enter
urls.path()
'/'
'/search?q=%23ASUcis355'
'/asu-cis-355/course-info'
I have defined a class to do this; however, I receive an error saying 'scheme() missing 1 required positional argument: 'self' Below is my class and the def parts to it that I have created.
class urls:
def __init__(self,url):
self.urls=urls
def scheme(self):
return urls.split("://")[0]
def server(self):
return urls.split("/")[2]
def path(self):
return urls.split(".com/")[1]
Any help at all is greatly appreciated!
This exists already. It's called urlparse:
from urllib.parse import urlparse
d = urlparse('https://twitter.com/search?q=%23ASUcis355')
print(d)
Output:
ParseResult(scheme='https', netloc='twitter.com', path='/search', params='', query='q=%23ASUcis355', fragment='')
If you attempt to call a class definition (what urls' is) without creating an instance of this class in Python3 then you get this error
>>> urls.scheme()
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: scheme() missing 1 required positional argument: 'self'
>>>
But if you create an instance of urls and then use that instance this works as intended
>>> url_instance = urls("http://www.google.com")
>>> url_instance.scheme()
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "<stdin>", line 5, in scheme
AttributeError: type object 'urls' has no attribute 'split'
Note that this fixes your current error but your code isn't correct as is. I'll leave you to figure out what's happening with this error.
The difference between a class definition (or type) and an instance of the class has some interesting nuance but generally speaking
class Thing:
pass
is a class definition and
thing_instance = Thing()
Is an instance of the class.

What exactly does "AttributeError: temp instance has no attribute '__getitem__'" mean?

I'm trying to understand a problem I'm having with python 2.7 right now.
Here is my code from the file test.py:
class temp:
def __init__(self):
self = dict()
self[1] = 'bla'
Then, on the terminal, I enter:
from test import temp
a=temp
if I enter a I get this:
>>> a
<test.temp instance at 0x10e3387e8>
And if I try to read a[1], I get this:
>>> a[1]
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
AttributeError: temp instance has no attribute '__getitem__'
Why does this happen?
First, the code you posted cannot yield the error you noted. You have not instantiated the class; a is merely another name for temp. So your actual error message will be:
TypeError: 'classobj' object has no attribute '__getitem__'
Even if you instantiate it (a = temp()) it still won't do what you seem to expect. Assigning self = dict() merely changes the value of the variable self within your __init__() method; it does not do anything to the instance. When the __init__() method ends, this variable goes away, since you did not store it anywhere else.
It seems as if you might want to subclass dict instead:
class temp(dict):
def __init__(self):
self[1] = 'bla'

Python: dynamically add attributes to new-style class/obj

Can I dynamically add attributes to instances of a new-style class (one that derives from object)?
Details:
I'm working with an instance of sqlite3.Connection. Simply extending the class isn't an option because I don't get the instance by calling a constructor; I get it by calling sqlite3.connect().
Building a wrapper doesn't save me much of the bulk for the code I'm writing.
Python 2.7.1
Edit
Right answers all. But I still am not reaching my goal; instances of sqlite3.Connection bar my attempts to set attributes in the following ways (as do instances of object itself). I always get an AttributeError:
> conn = sqlite3.connect([filepath])
> conn.a = 'foo'
Traceback (most recent call last):
File "<pyshell#2>", line 1, in <module>
conn.a = 'foo'
AttributeError: 'object' object has no attribute 'a'
> conn.__setattr__('a','foo')
Traceback (most recent call last):
File "<pyshell#2>", line 1, in <module>
conn.__setattr__('a','foo')
AttributeError: 'object' object has no attribute 'a'
Help?
Yes, unless the class is using __slots__ or preventing attribute writing by overriding __setattr__, or an internal Python class, or a Python class implemented natively (usually in C).
You can always try setting an attribute. Except for seriously weird __setattr__ implementations, assigning an attribute to an instance of a class of one of the types mentioned above should raise an AttributeError.
In these cases, you'll have to use a wrapper, like this:
class AttrWrapper(object):
def __init__(self, wrapped):
self._wrapped = wrapped
def __getattr__(self, n):
return getattr(self._wrapped, n)
conn = AttrWrapper(sqlite3.connect(filepath))
Simple experimentation:
In []: class Tst(object): pass
..:
In []: t= Tst()
In []: t.attr= 'is this valid?'
In []: t.attr
Out[]: 'is this valid?'
So, indeed it seems to be possible to do that.
Update:
But from the documentation: SQLite is a C library that ..., so it seems that you really need to wrap it.
conn.a = 'foo',
or any dynamic assignment is valid, if conn is
<type 'classobj'>.
Things like:
c=object()
c.e=1
will raise an Attribute error. On the otherhand: Python allows you to do fantastic Metaclass programming:
>>>from new import classobj
>>>Foo2 = classobj('Foo2',(Foo,),{'bar':lambda self:'bar'})
>>>Foo2().bar()
>>>'bar'
>>>Foo2().say_foo()
>>>foo

Categories

Resources