How could I convert the output of pickle.dumps into a string. I need to convert the output to a string.
Current, this what I got:
import pickle
class TestClass:
def __init__(self, number):
self.number = number
t1 = TestClass(14)
s1 = pickle.dumps(t1)
str_version = s1.decode('utf-8', 'backslashreplace')
print(pickle.loads(str_version.encode('utf-8', 'backslashreplace')))
But I'm getting the error:
Traceback (most recent call last):
File "C:\Users\ketha\Downloads\python_testing.py", line 11, in <module>
print(pickle.loads(str_version.encode('utf-8', 'backslashreplace')))
_pickle.UnpicklingError: invalid load key, '\x5c'.
I think this is because when I convert it to a string, it converts \x5c (for example) to \\x5c and doesn't undo this during decoding. How could I undo this?
I got some code working. Code:
import pickle
import sys
class TestClass:
def __init__(self, number):
self.number = number
t1 = TestClass(14)
s1 = pickle.dumps(t1)
str_version = s1.decode('unicode_escape')
decoded = pickle.loads(str_version.encode('utf-8', 'unicode_escape').replace(b'\xc2', b''))
print(decoded.number)
Related
I'm doing research on palmprint recognition. for that I use the edcc library for the introduction of the palmprint. but i have problem in saving the encoding result from palm. I want to save the encoding result into a file, but I get an error like below
Traceback (most recent call last):
File "/home/pi/Coba/PalmDetection/PalmRecognition.py", line 18, in <module>
pickle.dump(one_palmprint_code, config_dictionary_file)
_pickle.PicklingError: Can't pickle <class 'ctypes.c_char_Array_849'>: attribute lookup c_char_Array_849 on ctypes failed
My code like this :
import os
import edcc
import cv2
import pickle
TEST_PALMPRINT_DATA_DIR = "/home/pi/Coba/PalmDetection/Data"
TEST_A_01_PALMPRINT_IMAGE = os.path.join(TEST_PALMPRINT_DATA_DIR, "Palm1.jpeg")
#TEST_A_02_PALMPRINT_IMAGE = os.path.join(TEST_PALMPRINT_DATA_DIR, "a_02.bmp")
TEST_B_01_PALMPRINT_IMAGE = os.path.join(TEST_PALMPRINT_DATA_DIR, "palme.jpeg")
#TEST_B_02_PALMPRINT_IMAGE = os.path.join(TEST_PALMPRINT_DATA_DIR, "b_02.bmp")
if __name__ == "__main__":
config = edcc.EncoderConfig(29, 5, 5, 10)
encoder = edcc.create_encoder(config)
one_palmprint_code = encoder.encode_using_file(TEST_A_01_PALMPRINT_IMAGE)
with open('encode.encode', 'wb') as config_dictionary_file:
pickle.dump(one_palmprint_code, config_dictionary_file)
another_palmprint_code = encoder.encode_using_file(TEST_B_01_PALMPRINT_IMAGE)
similarity_score = one_palmprint_code.compare_to(another_palmprint_code)
print(
"{} <-> {} similarity score:{}".format(
TEST_A_01_PALMPRINT_IMAGE, TEST_B_01_PALMPRINT_IMAGE, similarity_score
)
)
What should i do?
The edcc module must use ctypes internally, but really should hide that fact instead of returning a ctypes-wrapped object. A ctypes.c_char_Array_849 is just a C-compatible wrapper around an array of bytes. You can access the equivalent Python bytes object via the .raw property (what edcc should return instead) and write that to the file:
import ctypes
import pickle
one_palmprint_code = (ctypes.c_char * 849)()
with open('encode.encode', 'wb') as config_dictionary_file:
#pickle.dump(one_palmprint_code, config_dictionary_file) # reproduces error
config_dictionary_file.write(one_palmprint_code.raw)
I'm trying to convert a Python object into C void pointer so that it would be callable from C API's, however the following code doesn't seem to work
from ctypes import *
class myclass:
def __init__(self):
self.val = 6
return
foo = myclass()
data = c_void_p(foo)
Output:
Traceback (most recent call last):
File "test.py", line 26, in <module>
data = c_void_p(foo)
TypeError: cannot be converted to pointer
I've also tried pointer() and byref(), but none of them works. How can I achieve what I'm trying to do? Thanks in advance.
Use data = ctypes.py_object(foo).
ctypes.py_object represents the PyObject * type in C.
I am making a project all in python 2.7 but it started to give some errors to me on the final parts since the documentation is in python 3.5. So i am changing everything to python 3.5, but it is giving me a error because of bytesIO. Can you help me to understand why, and what should i do? The error is coming from def repr on string_dinamica.write('P3\n'). I left all the code in case that it´s needed. Thanks for the help. NOTE: Just to confirm this works on python 2.7 but not in 3.5
from io import BytesIO
from cor_rgb_42347 import CorRGB
class Imagem:
def __init__(self, numero_linhas, numero_colunas):
self.numero_linhas = numero_linhas
self.numero_colunas = numero_colunas
self.linhas = []
for n in range(numero_linhas):
linha = []
for m in range(numero_colunas):
linha.append(CorRGB(0.0, 0.0, 0.0))
self.linhas.append(linha)
def __repr__(self):
string_dinamica = BytesIO()
string_dinamica.write('P3\n')
string_dinamica.write("#mcg#leim#isel 2015/16\n")
string_dinamica.write(str(self.numero_colunas) + " " \
+ str(self.numero_linhas) + "\n")
string_dinamica.write("255\n")
for linha in range(self.numero_linhas):
for coluna in range(self.numero_colunas):
string_dinamica.write(str(self.linhas[linha][coluna])+ " ")
string_dinamica.write("\n")
resultado = string_dinamica.getvalue()
string_dinamica.close()
return resultado
def set_cor(self, linha, coluna, cor_rgb):
"""Permite especificar a cor RGB do pixel na linha "linha",
coluna "coluna".
"""
self.linhas[linha-1][coluna-1] = cor_rgb
def get_cor(self, linha, coluna):
"""Permite obter a cor RGB do pixel na linha "linha",
coluna "coluna".
"""
return self.linhas[linha-1][coluna-1]
def guardar_como_ppm(self, nome_ficheiro):
"""Permite guardar a imagem em formato PPM ASCII num ficheiro.
"""
ficheiro = open(nome_ficheiro, 'w')
ficheiro.write(str(self))
ficheiro.close()
if __name__ == "__main__":
imagem1 = Imagem(5,5)
print(imagem1)
Traceback (most recent call last):
File "C:\Users\Utilizador\Desktop\Projectos Finais\Projecto_42347\imagem_42347.py", line 60, in <module>
print(imagem1)
File "C:\Users\Utilizador\Desktop\Projectos Finais\Projecto_42347\imagem_42347.py", line 19, in __repr__
string_dinamica.write('P3\n')
TypeError: a bytes-like object is required, not 'str'
For Python 3, just change BytesIO to StringIO. Python 3 strings are Unicode strings instead of byte strings, and __repr__ should return a Unicode string in Python 3.
If you try to return a bytes object like some other answers suggest, you will get:
TypeError: __repr__ returned non-string (type bytes)
As I mentioned on my comment, BytesIO requires byte-like object.
Demo:
>>> from io import BytesIO
>>>
>>> b = BytesIO()
>>>
>>> b.write('TEST\n')
Traceback (most recent call last):
File "<pyshell#97>", line 1, in <module>
b.write('TEST\n')
TypeError: 'str' does not support the buffer interface
>>>
>>>
>>> b.write(b'TEST\n')
5
>>> v = b.getbuffer()
>>>
>>> v[2:4]=b'56'
>>>
>>> b.getvalue()
b'TE56\n'
So add to the beginning of your the param. in you pass to write method, b(for binary).
I am trying to extend the Python datetime.timedelta for use with cross country race results. I want to construct an object from a string in format u"mm:ss.s". I am able to accomplish this using the factory design pattern and #classmethod annotation. How would I accomplish the same by overriding __init__ and/or __new__?
With the code below, constructing an object raises a TypeError. Note that __init__ is not called, because 'in my __init__' is not printed.
import datetime
import re
class RaceTimedelta(datetime.timedelta):
def __init__(self, timestr = ''):
print 'in my __init__'
m = re.match(r'(\d+):(\d+\.\d+)', timestr)
if m:
mins = int(m.group(1))
secs = float(m.group(2))
super(RaceTimedelta, self).__init__(minutes = mins, seconds = secs)
else:
raise ValueError('timestr not in format u"mm:ss.d"')
Here is the error:
>>> from mytimedelta import RaceTimedelta
>>> RaceTimedelta(u'24:45.7')
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: unsupported type for timedelta days component: unicode
>>>
If I move my code from __init__ to __new__, I get the following. Note that this time, the output shows that my __new__ function is called.
>>> RaceTimedelta(u'24:45.7')
in my __new__
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "mytimedelta.py", line 16, in __new__
super(RaceTimedelta, self).__new__(minutes = mins, seconds = secs)
TypeError: datetime.timedelta.__new__(): not enough arguments
>>>
Apparently timedelta objects are immutable, which means their value is actually set in the class' __new__() method—so you'll need to override that method instead of its __init__():
import datetime
import re
class RaceTimedelta(datetime.timedelta):
def __new__(cls, timestr=''):
m = re.match(r'(\d+):(\d+\.\d+)', timestr)
if m:
mins, secs = int(m.group(1)), float(m.group(2))
return super(RaceTimedelta, cls).__new__(cls, minutes=mins, seconds=secs)
else:
raise ValueError('timestr argument not in format "mm:ss.d"')
print RaceTimedelta(u'24:45.7')
Output:
0:24:45.700000
BTW, I find it odd that you're providing a default value for thetimestrkeyword argument that will be considered illegal and raise aValueError.
Sorry if this question is stupid. I created an unittest class which needs to take given inputs and outputs from outside. Thus, I guess these values should be initiated. However, I met some errors in the following code:
CODE:
import unittest
from StringIO import StringIO
##########Inputs and outputs from outside#######
a=[1,2]
b=[2,3]
out=[3,4]
####################################
def func1(a,b):
return a+b
class MyTestCase(unittest.TestCase):
def __init__(self,a,b,out):
self.a=a
self.b=b
self.out=out
def testMsed(self):
for i in range(self.tot_iter):
print i
fun = func1(self.a[i],self.b[i])
value = self.out[i]
testFailureMessage = "Test of function name: %s iteration: %i expected: %i != calculated: %i" % ("func1",i,value,fun)
self.assertEqual(round(fun,3),round(value,3),testFailureMessage)
if __name__ == '__main__':
f = MyTestCase(a,b,out)
from pprint import pprint
stream = StringIO()
runner = unittest.TextTestRunner(stream=stream, verbosity=2)
result = runner.run(unittest.makeSuite(MyTestCase(a,b,out)))
print 'Tests run', result.testsRun
However, I got the following error
Traceback (most recent call last):
File "C:testing.py", line 33, in <module>
result = runner.run(unittest.makeSuite(MyTestCase(a,b,out)))
File "C:\Python27\lib\unittest\loader.py", line 310, in makeSuite
return _makeLoader(prefix, sortUsing, suiteClass).loadTestsFromTestCase(testCaseClass)
File "C:\Python27\lib\unittest\loader.py", line 50, in loadTestsFromTestCase
if issubclass(testCaseClass, suite.TestSuite):
TypeError: issubclass() arg 1 must be a class
Can anyone give me some suggestions? Thanks!
The root of the problem is this line,
result = runner.run(unittest.makeSuite(MyTestCase(a,b,out)))
unittest.makeSuite expects a class, not an instance of a class. So just MyTestCase, not MyTestCase(a, b, out). This means that you can't pass parameters to your test case in the manner you are attempting to. You should probably move the code from init to a setUp function. Either access a, b, and out as globals inside setUp or take a look at this link for information regarding passing parameters to a unit test.
By the way, here is the source file within python where the problem originated. Might be informative to read.