I would like to write a function to build a bytes type string that need to use f-string with different value. the only way I can think about is like following code. anyone have better
suggestion? In code, I have string like I have level but in my actual code the string is about 600 charactors
def get_level_string(x):
size = dict(v1=1, v2= 200, v3= 30000)
s = size.get('v1')
name = lambda x: f"I have level value as {x} in the house"
return {
'level1': b'%a' % (name(size['v1'])),
'level2': b'%a' % (name(size['v2'])),
'level3': b'%a' % (name(size['v3'])),
}[x]
a = get_level_string('level1')
b = get_level_string('level2')
c = get_level_string('level3')
print(a, type(a))
print(b, type(b))
print(c, type(c))
=> #b"'I have level value as 1 in the house'" <class 'bytes'>
=> #b"'I have level value as 200 in the house'" <class 'bytes'>
=> #b"'I have level value as 30000 in the house'" <class 'bytes'>
You can make this a good deal simpler, by generating the strings and then calling their encode method to make them bytes objects. Note that your function really just builds a dictionary and then looks stuff up in it. It's much simpler to build the dictionary only once and then supply the bound __getitem__ method under a different name.
template = "I have level value as {} in the house"
size_list = (1, 200, 30000)
sizes = {f"level{i}": template.format(x).encode() for i, x in enumerate(size_list, start=1)}
get_level_string = sizes.__getitem__
# tests
a = get_level_string('level1')
b = get_level_string('level2')
c = get_level_string('level3')
print(a, type(a))
print(b, type(b))
print(c, type(c))
prints
b'I have level value as 1 in the house' <class 'bytes'>
b'I have level value as 200 in the house' <class 'bytes'>
b'I have level value as 30000 in the house' <class 'bytes'>
for your tests
Related
While working on a difference engine to identify differences in very large data structures, I noticed that a type comparison between identical-but-redeclared namedtuples misbehaves. Redeclaring the namedtuples is unavoidable*. Here is a minimal example:
def test_named_tuples_same_type():
from collections import namedtuple
X = namedtuple("X", "x")
a = X(1)
# We are unable to avoid redeclaring X
X = namedtuple("X", "x")
b = X(1)
print(repr(a))
print(repr(b))
# X(x=1)
# X(x=1)
assert isinstance(type(a), type(b)) # fail
assert type(a) == type(b) # fail
The asserts return:
> assert isinstance(type(a), type(b)) # fail
E AssertionError: assert False
E + where False = isinstance(<class 'tests.test_deep_diff.X'>, <class 'tests.test_deep_diff.X'>)
E + where <class 'tests.test_deep_diff.X'> = type(X(x=1))
E + and <class 'tests.test_deep_diff.X'> = type(X(x=1))
and
> assert type(a) == type(b) # fail
E AssertionError: assert <class 'tests.test_deep_diff.X'> == <class 'tests.test_deep_diff.X'>
How to assert the type of both are equal or semantically equal (without str(type()))?
*Redeclaring the namedtuple is unavoidable because it takes place in unmodifiable exec'd code to generate the data structures being diffed.
It isn't entirely clear what you mean by semantically equivalent precisely. But consider:
>>> from collections import namedtuple
>>> X1 = namedtuple("X", "x")
>>> X2 = namedtuple("X", "x")
Then you can use something like:
>>> def equivalent_namedtuple_types(t1, t2):
... return (t1.__name__, t1._fields) == (t2.__name__, t2._fields)
...
>>> equivalent_namedtuple_types(X1, X2)
True
>>>
From your comments, it seems like you may care about the .__module__ attribute as well.
I'm trying to get the name of a enum given one of its multiple values:
class DType(Enum):
float32 = ["f", 8]
double64 = ["d", 9]
when I try to get one value giving the name it works:
print DType["float32"].value[1] # prints 8
print DType["float32"].value[0] # prints f
but when I try to get the name out of a given value only errors will come:
print DataType(8).name
print DataType("f").name
raise ValueError("%s is not a valid %s" % (value, cls.name))
ValueError: 8 is not a valid DataType
ValueError: f is not a valid DataType
Is there a way to make this? Or am I using the wrong data structure?
The easiest way is to use the aenum library1, which would look like this:
from aenum import MultiValueEnum
class DType(MultiValueEnum):
float32 = "f", 8
double64 = "d", 9
and in use:
>>> DType("f")
<DType.float32: 'f'>
>>> DType(9)
<DType.double64: 'd'>
As you can see, the first value listed is the canonical value, and shows up in the repr().
If you want all the possible values to show up, or need to use the stdlib Enum (Python 3.4+), then the answer found here is the basis of what you want (and will also work with aenum):
class DType(Enum):
float32 = "f", 8
double64 = "d", 9
def __new__(cls, *values):
obj = object.__new__(cls)
# first value is canonical value
obj._value_ = values[0]
for other_value in values[1:]:
cls._value2member_map_[other_value] = obj
obj._all_values = values
return obj
def __repr__(self):
return '<%s.%s: %s>' % (
self.__class__.__name__,
self._name_,
', '.join([repr(v) for v in self._all_values]),
)
and in use:
>>> DType("f")
<DType.float32: 'f', 8>
>>> Dtype(9)
<DType.float32: 'd', 9>
1 Disclosure: I am the author of the Python stdlib Enum, the enum34 backport, and the Advanced Enumeration (aenum) library.
Goal:
(In Python 3.6)
Determine if the string passed to the function should be interpreted as an Int, Float or String.
Hopefully (with a builtin Python functions) without needed to write my own function which walks chars in Python.
Basically, like the C atoi() and atoll() functions, if the entire buffer is successfully read.
Should mark as Int:
"-1234"
"1234"
"+1234"
Should mark as Float:
"-1.234"
"1.234"
"+1.234"
Should mark as string:
"972-727-9857"
"1_2345"
"asdf"
Tried:
Using casts:
def find_type(s):
try:
int(s)
return int
except ValueError:
pass
try:
float(s)
return float
except ValueError:
pass
return str
^ the above has the drawback:
"1_234" -> int(1234)
Using AST
import ast
def find_type(s):
obj_type = ast.literal_eval(s)
if isinstance(obj_type, float):
return float
if isinstance(obj_type, int):
return int
return str
^ this also has issues with:
"123_123" -> int(123123)
"123-123-123" -> int(-123)
Question
Am I just doomed to write my own function which walks chars? ... I am about to just write this in C...
How do I parse a string to a float or int?
^ I found the above, but it doesn't quite solve my problem.
Just check for the underscore:
def find_type(s):
if '_' in s:
return str
for typ in (int,float):
try:
typ(s)
return typ
except ValueError:
pass
return str
trials = '-1234','1234','+1234','-1.234','1.234','+1.234','972-727-9857','1_2345','asdf'
for trial in trials:
print(trial,find_type(trial))
Output:
-1234 <class 'int'>
1234 <class 'int'>
+1234 <class 'int'>
-1.234 <class 'float'>
1.234 <class 'float'>
+1.234 <class 'float'>
972-727-9857 <class 'str'>
1_2345 <class 'str'>
asdf <class 'str'>
Hrmm... after posting this question, I thought of this:
With Regex:
import re
int_regex = re.compile(r'^(-|\+)?[0-9]+$')
float_regex = re.compile(r'^(-|\+)?([0-9]+)?\.[0-9]+$')
def find_type(s):
if re.match(int_regex, s):
return int
if re.match(float_regex, s):
return float
return str
I guess this is probably the only/best way.
I have a code line
emp_id=1
tp = type(emp_id)
print(tp)
print(type(tp))
strg = str(tp)
print(strg)
print(type(strg))
The result is as below
<class 'int'>
<class 'type'>
<class 'int'>
<class 'str'>
**What i need is i want to store in a string.
How to do it? **
The function type(x) returns the class of which the object x is an instance. All classes in python have the property __name__ which returns the actual name (as a string) of that class.
x = 1
tp = type(x).__name__
print(tp)
This will print: int
I generated a hash value for a file in python. The value consists of both characters and numbers. If i check the data type of each value, it is showing as string for both letters and numbers. How do I convert the data type of numbers from string to int?
Thanks in Advance!
import hashlib
myl = []
fobj = open('akash.txt','r')
buffer = fobj.read()
hsh = hashlib.sha512()
hsh.update(buffer.encode('utf-8'))
val = hsh.hexdigest()
for i in val:
print(type(i))
fobj.close()
The hash value generated by the code is:
cf83e1357eefb8bdf1542850d66d8007d620e4050b5715dc83f4a921d36ce9ce47d0d13c5d85f2b0ff8318d2877eec2f63b931bd47417a81a538327af927da3e
I expect the output to be as
<class 'str'>
<class 'str'>
<class 'int'>
...
But this is the output Im getting
<class 'str'>
<class 'str'>
<class 'str'>
...
I truly have no idea why you would want to do this, but you can try if you can convert a character in the hash string to an integer first and then print the type. Just change your loop as follows
for i in val:
try:
n = int(i)
except ValueError:
n = i
print(f'character: {n} is {type(n)}')