在Python中使用具有不同变量类型的ConfigParser(Use ConfigParser with different variable types in Python)
我想在以下情况下使用
ConfigParser
。 我运行一些代码之后,我有一个对象具有几个属性。 我挑选出其中的一些属性,并使用configparser
将它们写入.ini
文件。 这工作正常,我的.ini
文件看起来像这样。[Section] path = "D:\\" number = 10.0 boolean = False
然后用其他一些脚本,我想读取文件,并使用另一个对象(self)作为属性添加项目。
parser.read('file.ini') self.__dict__.update(dict(parser.items("Section")))
这会失败,因为所有值都由configparser作为字符串读取,现在所有属性都是字符串。
parser.items("Section")
看起来像这样:[('path', '"D:\\"'), ('number', '10.0'), ('boolean', 'False')]
现在我可以通过键指定浮点数,整数和布尔值,并使用相应的方法
parser.getfloat
,getint
和getboolean
来获取正确的python类型。 但是,这意味着要创建一个额外的键列表和一个循环来获取每个数据类型的数据类型,这是我不想要的。 此外,即使路径现在双引号,我需要开始删除引号。这种行为使
ConfigParser
对我来说几乎完全没有价值,而且我怀疑我是否正确使用它,如果ConfigParser
是我的目标的最佳选择,那就是将对象属性写入文件,稍后再读取文件并添加作为属性的新对象的参数。 我可以有效地使用ConfigParser
吗? 或者我应该开始寻找一种不同的方法?I am trying to use
ConfigParser
in the following situation. I am running some code after which i have an object with several attributes. I pick out some of these attributes and write them to a.ini
file withconfigparser
. This works fine and my.ini
file looks something like this.[Section] path = "D:\\" number = 10.0 boolean = False
Then with some other script I want to read the file and add the items as attributes to another object (self) using.
parser.read('file.ini') self.__dict__.update(dict(parser.items("Section")))
This fails because all values are read as strings by configparser and now all attributes are strings.
parser.items("Section")
looks like this:[('path', '"D:\\"'), ('number', '10.0'), ('boolean', 'False')]
Now I could go and specify the floats, integers, and booleans by their keys and use the corresponding methods
parser.getfloat
,getint
, andgetboolean
to get the right python types out. However, that means making an extra list of keys and a loop to get them for each data type, which i don't want. Furthermore, even the path is now double quoted and i need to start removing quotes.This behavior makes
ConfigParser
almost completely worthless to me and I am doubting if I am using it correctly an ifConfigParser
is the best option for my goal, which is simply to write object attributes to a file and at a later time read the file and add the parameters to a new object as attributes. Can I useConfigParser
for this effectively? Or should I start looking for a different method?
原文:https://stackoverflow.com/questions/45416943
最满意答案
myclass.h
#ifndef __MYCLASS_H__ #define __MYCLASS_H__ class MyClass { public: MyClass(); /* use virtual otherwise linker will try to perform static linkage */ virtual void DoSomething(); private: int x; }; #endif
myclass.cc
#include "myclass.h" #include <iostream> using namespace std; extern "C" MyClass* create_object() { return new MyClass; } extern "C" void destroy_object( MyClass* object ) { delete object; } MyClass::MyClass() { x = 20; } void MyClass::DoSomething() { cout<<x<<endl; }
class_user.cc
#include <dlfcn.h> #include <iostream> #include "myclass.h" using namespace std; int main(int argc, char **argv) { /* on Linux, use "./myclass.so" */ void* handle = dlopen("myclass.so", RTLD_LAZY); MyClass* (*create)(); void (*destroy)(MyClass*); create = (MyClass* (*)())dlsym(handle, "create_object"); destroy = (void (*)(MyClass*))dlsym(handle, "destroy_object"); MyClass* myClass = (MyClass*)create(); myClass->DoSomething(); destroy( myClass ); }
在Mac OS X上编译:
g++ -dynamiclib -flat_namespace myclass.cc -o myclass.so g++ class_user.cc -o class_user
在Linux上编译:
g++ -fPIC -shared myclass.cc -o myclass.so g++ class_user.cc -ldl -o class_user
如果这是一个插件系统,你可以使用MyClass作为基类,并定义所有必需的函数virtual。 插件作者然后从MyClass派生,重写虚拟并实现
create_object
和destroy_object
。 您的主要应用程序不需要以任何方式进行更改。myclass.h
#ifndef __MYCLASS_H__ #define __MYCLASS_H__ class MyClass { public: MyClass(); /* use virtual otherwise linker will try to perform static linkage */ virtual void DoSomething(); private: int x; }; #endif
myclass.cc
#include "myclass.h" #include <iostream> using namespace std; extern "C" MyClass* create_object() { return new MyClass; } extern "C" void destroy_object( MyClass* object ) { delete object; } MyClass::MyClass() { x = 20; } void MyClass::DoSomething() { cout<<x<<endl; }
class_user.cc
#include <dlfcn.h> #include <iostream> #include "myclass.h" using namespace std; int main(int argc, char **argv) { /* on Linux, use "./myclass.so" */ void* handle = dlopen("myclass.so", RTLD_LAZY); MyClass* (*create)(); void (*destroy)(MyClass*); create = (MyClass* (*)())dlsym(handle, "create_object"); destroy = (void (*)(MyClass*))dlsym(handle, "destroy_object"); MyClass* myClass = (MyClass*)create(); myClass->DoSomething(); destroy( myClass ); }
On Mac OS X, compile with:
g++ -dynamiclib -flat_namespace myclass.cc -o myclass.so g++ class_user.cc -o class_user
On Linux, compile with:
g++ -fPIC -shared myclass.cc -o myclass.so g++ class_user.cc -ldl -o class_user
If this were for a plugin system, you would use MyClass as a base class and define all the required functions virtual. The plugin author would then derive from MyClass, override the virtuals and implement
create_object
anddestroy_object
. Your main application would not need to be changed in any way.
相关问答
更多-
C允许从void *到任何指针类型(包括函数指针)的隐式转换; C ++需要显式投射。 正如leiflundgren所说,您需要将dlsym()的返回值转换为您需要的函数指针类型。 许多人发现C的函数指针语法很尴尬。 一种常见的模式是键入功能指针: typedef double (*cosine_func_ptr)(double); 您可以将函数指针变量cosine定义为类型的成员: cosine_func_ptr cosine; 并使用该类型而不是笨拙的函数指针语法进行投射: cosine = (co ...
-
如何根据需要从C ++函数/ Qt方法加载动态库(How to load a dynamic library on demand from a C++ function/Qt method)[2023-04-03]
你想要无样板延迟加载。 在Windows上,MSVC通过发出通过函数指针解析函数的存根来实现延迟加载 。 你也可以做到的。 首先,让我们观察一下,如果你所做的只是调用它们,函数指针和函数是可以互换的。 调用函数或函数指针的语法是相同的: void foo_impl() {} void (*foo)() = foo_impl; int main() { foo_impl(); foo(); } 我们的想法是将函数指针最初设置为thunk,它将在运行时解析实际函数: extern void (*fo ... -
myclass.h #ifndef __MYCLASS_H__ #define __MYCLASS_H__ class MyClass { public: MyClass(); /* use virtual otherwise linker will try to perform static linkage */ virtual void DoSomething(); private: int x; }; #endif myclass.cc #include "myclass.h ...
-
在第5步中,您忘记了-L. 在当前目录中查找库。 默认情况下,搜索库时仅使用[long]系统目录列表。 您还需要添加. 在执行程序之前到LD_LIBRARY_PATH环境变量,以便在运行时搜索当前目录。 运行ldconfig将避免这种情况,但如果您只是测试您的库并且不想持续影响您的系统,我会坚持使用LD_LIBRARY_PATH方法。 另一种方法是将您的库“安装”到其中一个目录中,例如/usr/local/lib (或等效的)。 执行此操作后应使用ldconfig ,以便为您设置动态库缓存和所有符号链接。 ...
-
你可以阅读: 大会HowTo 从Powerup到Bash提示 Wikipedia关于系统调用 , Linux内核 , 虚拟内存 , 地址空间 , 进程 , 编译器 , 链接器 , 汇编语言 , GCC , ELF Levine关于连接器和装载机的书 x86-84 ,特别是关于x86-64 ABI规范 高级Linux编程书 几个系统调用(2)手册页,特别是介绍(2) , execve(2) , mmap(2) , fork(2) ELF病毒撰写指南 GCC文件 (特别是内部) Binutils文档 程序库Ho ...
-
将共享库作为C ++插件使用(Go shared library as C++ plugin)[2022-10-15]
我不认为你可以将Go嵌入到C中。但是,你可以将C嵌入到Go中,并且可以使用一个存根C程序将它调用到C中,这是下一个最好的事情! Cgo肯定支持与共享库链接,所以也许这种方法适用于你。 喜欢这个 main.go // Stub go program to call cmain() in C package main // extern int cmain(void); import "C" func main() { C.cmain() } main.c中 #include... -
共享库发现(Shared Library Discovery)[2022-06-08]
AFAIK,没有glibc函数来枚举.so文件的所有公共接口函数。 您可以参考libelf从动态文件中读取所有符号。 Libelf在这里http://www.mr511.de/software/ 。 找到符号后,可以使用dlopen和dlsym来加载它。 AFAIK, there is no glibc function to enumerate all the public interface functions for a .so file. You can refer to libelf to rea ... -
所以,我设法通过大量试验和错误提出了一个有效的解决方案。 对于任何在将来偶然发现这一点的人来说,下面是对我有用的东西。 概观 我最终使用了System-V“SHM风格”的共享内存。 事实证明,此内存与正在运行的系统一起存储,直到它被明确删除(或系统重新启动)。 我附加的任何过程,只要它在附加时提供适当的密钥。 问题的答案 (1)否,并不总是需要一个正在运行的进程来保留与系统一起存储的内存。 (2)当各种调用进入/退出时,重复连接/分离共享内存段。 这些动作都不会导致内存被破坏; 它被保留在系统中,直到被明确 ...
-
linux上的共享库问题(shared library problems on linux)[2022-05-18]
从字面上看,链接器可能正在寻找“libXaw.so”。 是在/ usr / lib中吗? 如果没有,您可以尝试将其添加为libXaw7.so.7.0.0中的另一个软链接。 The linker may be looking, literally, for "libXaw.so". Is that in /usr/lib? If not, you could try adding it as another soft link from libXaw7.so.7.0.0. -
你正在尝试做什么应该没有问题: app.c: #include "staticlib.h" #include "stdio.h" int main() { printf("and the magic number is: %d\n",doSomethingDynamicish()); return 0; } staticlib.h: #ifndef __STATICLIB_H__ #define __STATICLIB_H__ int doSomethingDynamicish(); #endif ...