So i have been struggling with Python more and more as i come from very much a Non Object Oriented Background (I write C and C++11 Applications in C Style :P)
Now i have recently decided to try out the Struct Module and i honestly find it very confusing honestly when comparing it to C or C++ due to the fact that you cannot declare Datatypes sadly :(
In the past, I've used Python's struct module as an example when asked if there are any benefits of dynamic typing. It provides functions to convert between sequences of bytes and Python values, controlled by a compact "format string". Lua also supports very similar conversions via the string.pack & unpack functions.
For example, these few lines of Python are all it takes to interpret the header of a BMP image file and output the image's dimensions. Of course for this particular example it's easier to use an image library, but this code is much more flexible - it can be changed to support custom file types, and iteratively modified to investigate files of unknown type:
file_name = input('File name: ')
with open(file_name, 'rb') as f:
signature, _, _, header_size, width, height = struct.unpack_from('<2sI4xIIii', f.read())
assert signature == b'BM' and header_size == 40
print(f'Dimensions: {width}x{abs(height)}')Are there statically-typed languages that can offer similarly concise code for binary manipulation? I can see a couple of ways it could work:
-
Require the format string to be a compile-time constant. The above call to
unpack_fromcould then returnTuple<String, Int, Int, Int, Int, Int> -
Allow fully general format strings, but return
List<Object>and require the programmer to cast theObjects to the correct type:assert (signature as String) == 'BM' and (header_size as Int) == 40 print(f'Dimensions: {width as Int}x{abs(height as Int)}')
Is it possible for a statically-typed language to support a function like struct.unpack_from? The ones I'm familiar with require much more verbose code (e.g. defining a dataclass for the header layout). Or is there a reason that it's not possible?
In perl one can use the 'Class::Struct' library to a large degree as if it were a C-style struct. However the syntax is not the most comfortable.
Is it possible to do the same thing in Python, but using the native 'Class' keyword?
A quick look at the documentation suggests this may work:
Class SettingsStructure:
DataMemberOne = 0
DataMemberTwo = 0Then later in the same programme:
Settings = SettingsStructure() Settings.DataMemberOne = 10 Settings.DataMemberTwo = 20
Is that possible?
Hi, I came from Python to C++, and was hoping someone could explain what "struct" is in relative terms to Python.
Why not? Classes are fine for that.
If you want to save some memory, you might also want to use __slots__ so the objects don't have a __dict__. See http://docs.python.org/reference/datamodel.html#slots for details and Usage of __slots__? for some useful information.
For example, a class holding only two values (a and b) could looks like this:
class AB(object):
__slots__ = ('a', 'b')
If you actually want a dict but with obj.item access instead of obj['item'], you could subclass dict and implement __getattr__ and __setattr__ to behave like __getitem__ and __setitem__.
dataclass is now built-in to Python as of Python 3.7!
from dataclasses import dataclass
@dataclass
class EZClass:
name: str='default'
qty: int
Test:
classy = EZClass('cars', 3)
print(classy)
Output:
EZClass(name='cars', qty=3)
Besides for the automatic initialization and __repr__ methods which it generates, it also automatically creates an __eq__ method to make it simple and intuitive to compare two instances of the class.
See PEP 557.
Backported to Python 3.6 using the dataclasses package.
For example, if I did:
typedef struct{
double xCoordinate;
double yCoordinate;
double zCoordinate;
}coordinates;How would I do the same code in Python?