首页 最新 热门 推荐

  • 首页
  • 最新
  • 热门
  • 推荐

Python-VBA函数之旅-repr函数

  • 25-03-03 04:23
  • 3542
  • 5850
blog.csdn.net

目录

一、repr函数的常见应用场景

二、repr函数使用注意事项

三、如何用好repr函数?

1、repr函数:

1-1、Python:

1-2、VBA:

2、推荐阅读:

个人主页:https://blog.csdn.net/ygb_1024?spm=1010.2135.3001.5421

一、repr函数的常见应用场景

        repr函数在Python中有多种实际应用场景,常见的应用场景有:

1、调试和日志记录:当在开发过程中需要记录或调试对象的状态时,repr()函数可以提供一个清晰、易于理解的字符串表示,这有助于识别对象是否按预期被创建和修改。

2、创建有效的Python代码:由于repr()函数通常返回一个有效的Python表达式,因此它可以用于创建或修改Python代码。例如,如果你有一个字典或列表,并希望将其转换为Python源代码中的表示形式,你可以使用repr()函数。

3、自定义对象的字符串表示:通过为自定义类实现__repr__()方法,你可以控制当对象被repr()函数调用时返回的字符串,这对于创建用户友好的输出或确保对象可以被准确地重新创建(通过 eval(repr(obj)))非常有用。

4、数据持久化:虽然repr()函数不应被用作通用的序列化机制(因为有更健壮的库如pickle或 json),但在某些情况下,将对象转换为repr()字符串可以作为一种简单的持久化方法。例如,如果你有一个简单的数据结构,并且只需要在同一Python环境中重新加载它,那么使用repr()函数可能就足够了。

5、文档和示例:在编写文档或示例代码时,使用repr()函数可以自动获取对象的字符串表示,而无需手动编写它,这有助于确保文档中的示例与实际代码保持一致。

6、用户界面和命令行工具:在构建需要显示对象信息的用户界面或命令行工具时,repr()函数可以提供一个简洁、一致的表示形式。例如,一个命令行工具可能会使用repr()函数来显示其内部数据结构的当前状态。

7、测试和断言:在编写测试时,repr()可以用于比较对象的预期值和实际值,虽然更常见的是使用 `==` 运算符或专门的断言函数(如assertEqual),但在某些情况下,比较对象的repr()表示可能更方便或更可靠。

8、交互式解释器:在Python的交互式解释器中,当你输入一个表达式并按下回车键时,它通常会显示该表达式的repr()表示,这使得你能够直观地看到表达式的值以及它的类型和其他属性。

        注意,虽然repr()函数在许多情况下都很有用,但也有一些限制和注意事项。例如,repr()函数的输出可能包含换行符和引号等特殊字符,这可能会使输出难以阅读或处理。此外,repr()函数的输出通常不是为人类用户设计的,而是为Python解释器设计的,因此,在需要向人类用户显示对象信息时,通常使用str()函数而不是repr()函数。

二、repr函数使用注意事项

        在使用Python中的repr()函数时,需牢记以下注意事项:

1、安全性:repr()函数返回的字符串通常是可以被eval()函数安全地执行的(尽管这并不意味着你应该总是使用eval()函数来处理repr()函数的输出,因为eval()函数本身就存在安全风险),但是,如果你将repr()函数的输出用于其他目的(如文件写入、网络传输等),则需要确保它不会造成安全问题。

2、可读性:虽然repr()函数返回的字符串通常是机器可读的,但它可能不总是人类可读的,对于复杂的对象,repr()函数的输出可能会很长且难以理解,因此,在需要向用户显示对象信息时,可能需要考虑使用其他方法(如自定义的__str__方法)来生成更友好的输出。

3、避免无限递归:如果你在自定义类的__repr__方法中使用了递归(即调用了自身的__repr__方法),则需要小心避免无限递归。例如,如果你有两个对象相互引用对方,并且它们的__repr__方法都试图包含对方的repr()表示,那么这将导致无限递归和栈溢出错误。

4、不要用于序列化:虽然repr()可以将对象转换为字符串表示,但它并不是一种通用的序列化方法;对于复杂的对象或包含不可序列化数据(如文件句柄、网络连接等)的对象,repr()的输出可能无法被正确地转换回原始对象,因此,在需要序列化对象时,应该使用专门的序列化库(如pickle、json等)。

5、自定义__repr__方法时要小心:当你为自定义类实现__repr__方法时,需要确保返回的字符串是有效的Python表达式,并且可以被eval()函数安全地执行(尽管你不应该总是依赖eval()),此外,你还应该考虑如何处理类的私有属性和敏感数据,以避免在repr()的输出中泄露这些信息。

6、区分__repr__和__str__:__repr__和__str__都是Python中用于定义对象字符串表示的特殊方法,但它们有不同的用途和约定:__repr__应该返回一个对象的官方、无歧义且通常可评估的字符串表示,而__str__则应该返回一个对用户友好的、易读的字符串表示,在编写自定义类时,你应该同时考虑这两个方法,并根据需要为它们提供不同的实现。

7、避免循环引用:在处理包含循环引用的数据结构时,实现__repr__方法时要特别小心;循环引用可能导致无限递归或无限增长的字符串表示,在这种情况下,您可能需要使用特殊的技巧或算法来生成有效的字符串表示。

三、如何用好repr函数?

        要充分利用Python中的repr()函数,需遵循以下建议:

1、理解repr()的目的:repr()函数的目的是返回一个对象的官方字符串表示,这通常是一个有效的Python表达式,可以重新创建该对象(尽管并不总是能精确重建)。

2、为自定义类实现__repr__方法:当你创建自定义类时,实现一个清晰的__repr__方法可以帮助你和其他开发者更容易地理解和调试代码,确保__repr__返回的字符串表示是准确、清晰且易于理解的,考虑包括类的名称和关键属性在字符串表示中。

3、注意安全性:避免将repr()函数的输出直接传递给eval()函数,除非你确定内容是安全的,当处理来自不可信来源的数据时,要特别小心。

4、测试__repr__方法:编写单元测试来验证你的__repr__方法是否返回预期的输出,确保 eval(repr(obj))能够重新创建原始对象(如果适用)。

5、避免无限递归:当处理递归数据结构时,确保__repr__方法有明确的终止条件,以避免无限递归。

6、优化性能:如果repr()的调用成为性能瓶颈,请考虑优化代码或使用其他替代方案,避免在 __repr__方法中执行复杂的计算或操作。

7、保持一致性:对于同一类型的对象,__repr__方法应该始终返回相同格式的字符串表示。

8、考虑使用pprint模块:如果需要更美观或更易读的输出,可以考虑使用pprint模块来打印复杂的数据结构,pprint模块提供了pprint()和pformat()函数,它们可以格式化输出,使其更易于阅读。

9、避免在用户界面中使用repr():通常,repr()函数返回的字符串表示是为了调试和日志记录而设计的,而不是为了向最终用户显示,在用户界面或向用户显示数据时,请考虑使用str()函数或自定义的格式化方法。

10、遵循PEP8风格指南:当实现__repr__方法时,请遵循 Python 的官方编码风格指南PEP8。例如,确保字符串表示中的类名、属性名和值之间使用适当的空格和标点符号。

        总之,只有通过遵循这些建议和实践,你才能更好地利用repr()函数,并在你的Python代码中获得更清晰、更易于理解和调试的字符串表示。

1、repr函数:
1-1、Python:
  1. # 1.函数:repr
  2. # 2.功能:用于将对象转化为供解释器读取的形式,通常表示为可打印的字符串
  3. # 3.语法:repr(object)
  4. # 4.参数:object,表示任何Python对象,你想要获取其repr表示法的对象
  5. # 5.返回值:返回一个对象的官方字符串表示形式,即字符串
  6. # 6.说明:
  7. # 7.示例:
  8. # 用dir()函数获取该函数内置的属性和方法
  9. print(dir(repr))
  10. # ['__call__', '__class__', '__delattr__', '__dir__', '__doc__', '__eq__', '__format__', '__ge__', '__getattribute__',
  11. # '__getstate__', '__gt__', '__hash__', '__init__', '__init_subclass__', '__le__', '__lt__', '__module__', '__name__',
  12. # '__ne__', '__new__', '__qualname__', '__reduce__', '__reduce_ex__', '__repr__', '__self__', '__setattr__', '__sizeof__',
  13. # '__str__', '__subclasshook__', '__text_signature__']
  14. # 用help()函数获取该函数的文档信息
  15. help(repr)
  16. # 应用一:调试和日志记录
  17. # 示例1:简单类与repr()
  18. class Person:
  19. def __init__(self, name, age):
  20. self.name = name
  21. self.age = age
  22. def __repr__(self):
  23. return f"Person(name={self.name!r}, age={self.age})"
  24. # 使用示例
  25. p = Person("Myelsa", 18)
  26. print(repr(p))
  27. # Person(name='Myelsa', age=18)
  28. # 示例2:使用logging模块与repr()
  29. import logging
  30. class Circle:
  31. def __init__(self, radius):
  32. self.radius = radius
  33. def __repr__(self):
  34. return f"Circle(radius={self.radius})"
  35. # 配置logging
  36. logging.basicConfig(level=logging.INFO)
  37. # 创建一个Circle对象并使用logging记录其状态
  38. c = Circle(6)
  39. logging.info("Circle object: %s", repr(c))
  40. # INFO:root:Circle object: Circle(radius=6)
  41. # 示例3:调试时打印复杂数据结构
  42. data = [
  43. {"name": "Myelsa", "age": 18, "city": "Guangzhou"},
  44. {"name": "Bruce", "age": 6, "city": "Foshan"},
  45. # ... 更多的字典 ...
  46. ]
  47. # 使用repr()查看数据结构
  48. print(repr(data))
  49. # [{'name': 'Myelsa', 'age': 18, 'city': 'Guangzhou'}, {'name': 'Bruce', 'age': 6, 'city': 'Foshan'}]
  50. # 示例4:自定义repr()以隐藏敏感信息
  51. class User:
  52. def __init__(self, username, password):
  53. self.username = username
  54. self._password = password # 使用下划线前缀表示这是一个“私有”属性
  55. def __repr__(self):
  56. return f"User(username={self.username!r}, password=***)"
  57. # 使用示例
  58. u = User("[email protected]", "secret_password")
  59. print(repr(u))
  60. # User(username='[email protected]', password=***)
  61. # 应用二:创建有效的Python代码
  62. # 示例1:基础类型
  63. # 整数
  64. num = 42
  65. print(repr(num))
  66. # 浮点数
  67. float_num = 3.14159
  68. print(repr(float_num))
  69. # 字符串
  70. s = "Hello, world!"
  71. print(repr(s))
  72. # 42
  73. # 3.14159
  74. # 'Hello, world!'
  75. # 示例2:自定义类
  76. class Point:
  77. def __init__(self, x, y):
  78. self.x = x
  79. self.y = y
  80. def __repr__(self):
  81. return f"Point({self.x}, {self.y})"
  82. # 创建一个Point对象
  83. p = Point(1, 2)
  84. # 使用repr()获取其表示,并尝试用eval()重新创建它
  85. p_repr = repr(p)
  86. print(p_repr) # 输出: 'Point(1, 2)'
  87. try:
  88. p_new = eval(p_repr)
  89. print(p_new.x, p_new.y) # 输出: 1 2
  90. except NameError:
  91. # 注意:eval()在当前命名空间中找不到Point类时会抛出NameError
  92. # 为了使eval()工作,需要确保Point类在eval()的命名空间中可用
  93. pass
  94. # Point(1, 2)
  95. # 1 2
  96. # 示例3:包含复杂数据的类
  97. class Person:
  98. def __init__(self, name, age, friends=None):
  99. self.name = name
  100. self.age = age
  101. self.friends = friends if friends is not None else []
  102. def __repr__(self):
  103. return f"Person(name={self.name!r}, age={self.age}, friends=[{', '.join(repr(f) for f in self.friends)}])"
  104. # 创建一个Person对象,并为其添加一些朋友
  105. p = Person("Myelsa", 18)
  106. p.friends.append(Person("Bruce", 6))
  107. p.friends.append(Person("Jimmy", 15))
  108. # 使用repr()获取其表示
  109. p_repr = repr(p)
  110. print(p_repr)
  111. # Person(name='Myelsa', age=18, friends=[Person(name='Bruce', age=6, friends=[]), Person(name='Jimmy', age=15, friends=[])])
  112. # 应用三:自定义对象的字符串表示
  113. # 示例1:简单的自定义对象
  114. class Person:
  115. def __init__(self, name, age):
  116. self.name = name
  117. self.age = age
  118. def __repr__(self):
  119. return f"Person(name={self.name!r}, age={self.age})"
  120. # 创建一个Person对象
  121. p = Person("Myelsa", 18)
  122. # 打印对象的repr()表示
  123. print(repr(p))
  124. # Person(name='Myelsa', age=18)
  125. # 示例2:包含列表的自定义对象
  126. class Team:
  127. def __init__(self, name, members):
  128. self.name = name
  129. self.members = members
  130. def __repr__(self):
  131. return f"Team(name={self.name!r}, members=[{', '.join(repr(m) for m in self.members)}])"
  132. class Person:
  133. def __init__(self, name, age):
  134. self.name = name
  135. self.age = age
  136. def __repr__(self):
  137. return f"Person(name={self.name!r}, age={self.age})"
  138. # 创建一个Team对象,其中members是一个Person对象的列表
  139. p1 = Person("Myelsa", 18)
  140. p2 = Person("Bruce", 6)
  141. t = Team("Developers", [p1, p2])
  142. # 打印对象的repr()表示
  143. print(repr(t))
  144. # Team(name='Developers', members=[Person(name='Myelsa', age=18), Person(name='Bruce', age=6)])
  145. # 示例3:嵌套的自定义对象
  146. class Address:
  147. def __init__(self, street, city, country):
  148. self.street = street
  149. self.city = city
  150. self.country = country
  151. def __repr__(self):
  152. return f"Address(street={self.street!r}, city={self.city!r}, country={self.country!r})"
  153. class Employee:
  154. def __init__(self, name, age, address):
  155. self.name = name
  156. self.age = age
  157. self.address = address
  158. def __repr__(self):
  159. return f"Employee(name={self.name!r}, age={self.age}, address={repr(self.address)})"
  160. # 创建一个Address对象和一个Employee对象
  161. a = Address("123 Main St", "Springfield", "USA")
  162. e = Employee("Homer Simpson", 42, a)
  163. # 打印对象的repr()表示
  164. print(repr(e))
  165. # Employee(name='Homer Simpson', age=42, address=Address(street='123 Main St', city='Springfield', country='USA'))
  166. # 应用四:数据持久化
  167. # 示例1:使用repr()和文件进行数据持久化
  168. class Person:
  169. def __init__(self, name, age):
  170. self.name = name
  171. self.age = age
  172. def __repr__(self):
  173. return f"Person(name={self.name!r}, age={self.age})"
  174. # 创建一个Person对象
  175. p = Person("Myelsa", 18)
  176. # 将对象转换为repr()字符串并保存到文件中
  177. with open("person_data.txt", "w") as file:
  178. file.write(repr(p))
  179. # 从文件中读取repr()字符串并尝试重新创建对象
  180. # 注意:在实际应用中,你可能需要更健壮的错误处理
  181. with open("person_data.txt", "r") as file:
  182. data = file.read()
  183. try:
  184. p_recreated = eval(data)
  185. print(repr(p_recreated)) # 输出应该是和原始对象相同的repr()字符串
  186. except Exception as e:
  187. print(f"无法重新创建对象:{e}")
  188. # Person(name='Myelsa', age=18)
  189. # 应用五:文档和示例
  190. class Person:
  191. def __init__(self, name, age):
  192. self.name = name
  193. self.age = age
  194. def __repr__(self):
  195. """
  196. Return a string representation of the Person object that is suitable for
  197. printing and evaluation.
  198. Returns:
  199. str: A string representation of the Person object in the form
  200. 'Person(name="name", age=age)'.
  201. Examples:
  202. >>> p = Person("Myelsa", 18)
  203. >>> print(p)
  204. Person(name="Myelsa", age=18)
  205. >>> eval(repr(p)) == p # Warning: eval() can be unsafe, use with caution
  206. True
  207. """
  208. return f"Person(name={self.name!r}, age={self.age})"
  209. # 示例:在文档字符串中使用repr()
  210. if __name__ == "__main__":
  211. p = Person("Bruce", 6)
  212. print(p) # 这将调用Person类的__repr__方法
  213. # 在文档字符串中提到的示例
  214. print("--- Example from docstring ---")
  215. print(repr(p)) # 直接调用repr()函数来显示对象表示
  216. # 注意:虽然eval(repr(p))可以工作,但在实际中应避免使用eval()除非完全信任输入
  217. # print(eval(repr(p)) == p) # 这是一个不安全的示例,仅用于说明
  218. # 更好的方式是使用其他方法来重新创建对象,例如通过类的构造函数
  219. p_recreated = Person(**eval(repr(p).lstrip('Person(').rstrip(')').split(', ')))
  220. print(f"Recreated object: {p_recreated}")
  221. # 注意:上面的方法仍然使用了eval(),但在实践中,你通常会直接传递参数给构造函数
  222. # 应用六:用户界面和命令行工具
  223. class Person:
  224. def __init__(self, name, age):
  225. self.name = name
  226. self.age = age
  227. def __repr__(self):
  228. """
  229. Return a string representation of the Person object suitable for UI and CLI.
  230. """
  231. return f"Person(name={self.name}, age={self.age})"
  232. # 示例:在命令行工具中使用repr()
  233. if __name__ == "__main__":
  234. # 创建一个Person对象
  235. person = Person("Myelsa", 18)
  236. # 在命令行中直接打印对象,这会调用__repr__方法
  237. print(person) # 输出: Person(name=Myelsa, age=18)
  238. # 假设我们有一个简单的命令行界面,用户可以输入命令来查看对象的信息
  239. def cli_interface():
  240. while True:
  241. command = input("Enter command (or 'quit' to exit): ")
  242. if command == 'quit':
  243. break
  244. elif command == 'show_person':
  245. print(person) # 使用repr()来显示对象信息
  246. else:
  247. print("Unknown command.")
  248. # 启动命令行界面
  249. cli_interface()
  250. # 示例:在用户界面(UI)中使用repr()(虽然通常UI会使用更友好的展示方式)
  251. # 但为了演示,我们假设UI通过控制台输出信息
  252. def ui_display(obj):
  253. # 在UI中,我们可能希望显示更友好的信息,但这里仍然使用repr()作为例子
  254. print(f"Displayed object: {repr(obj)}")
  255. # 调用UI显示函数
  256. ui_display(person) # 输出: Displayed object: Person(name=Myelsa, age=18)
  257. # Person(name=Myelsa, age=18)
  258. # Enter command (or 'quit' to exit): show_person
  259. # Person(name=Myelsa, age=18)
  260. # Enter command (or 'quit' to exit): quit
  261. # Displayed object: Person(name=Myelsa, age=18)
  262. # 应用七:测试和断言
  263. import pytest
  264. class Person:
  265. def __init__(self, name, age):
  266. self.name = name
  267. self.age = age
  268. def __repr__(self):
  269. return f"Person(name={self.name!r}, age={self.age})"
  270. # 示例:在测试中使用repr()进行断言
  271. def test_person_repr():
  272. # 创建一个Person对象
  273. person = Person("Myelsa", 18)
  274. # 使用repr()获取对象的字符串表示
  275. person_repr = repr(person)
  276. # 进行断言,验证repr()的结果是否符合预期
  277. assert person_repr == "Person(name='Myelsa', age=18)", "The repr() of Person is not as expected."
  278. # 运行测试函数
  279. test_person_repr()
  280. def test_person_attributes():
  281. # 创建一个Person对象
  282. person = Person("Jimmy", 15)
  283. # 进行断言,验证对象的属性是否符合预期
  284. assert person.name == "Jimmy", "The name of the person is not as expected."
  285. assert person.age == 15, "The age of the person is not as expected."
  286. # 运行测试函数
  287. test_person_attributes()
  288. # Testing started at 12:01 ...
  289. # Launching pytest with arguments E:\python_workspace\pythonProject\test1.py --no-header --no-summary -q in E:\python_workspace\pythonProject
  290. #
  291. # ============================= test session starts =============================
  292. # collecting ... collected 2 items
  293. #
  294. # test1.py::test_person_repr PASSED [ 50%]
  295. # test1.py::test_person_attributes PASSED [100%]
  296. #
  297. # ============================== 2 passed in 0.10s ==============================
  298. # 应用八:交互式解释器
  299. class Person:
  300. def __init__(self, name, age):
  301. self.name = name
  302. self.age = age
  303. def __repr__(self):
  304. """
  305. Return a string representation of the Person object that is suitable for
  306. interactive interpreters.
  307. """
  308. return f"Person(name={self.name!r}, age={self.age})"
  309. # 创建一个Person对象
  310. p = Person("Myelsa", 18)
  311. # 尝试打印对象,这会隐式地调用__repr__方法
  312. print(p)
  313. # 你也可以显式地调用repr()函数
  314. print(repr(p))
  315. # 在交互式解释器中,你可以直接输入变量名来查看其repr表示
  316. # 输入:p
  317. # 使用repr()在交互式解释器中进行字符串操作或调试
  318. repr_string = repr(p)
  319. print(f"The representation of p is: {repr_string}")
  320. # 你还可以将repr表示用于日志记录、错误消息等
  321. import logging
  322. logging.basicConfig(level=logging.INFO)
  323. logging.info(f"Created a Person object: {p}")
  324. # 输出日志信息,其中包含了p的repr表示
  325. # Person(name='Myelsa', age=18)
  326. # Person(name='Myelsa', age=18)
  327. # The representation of p is: Person(name='Myelsa', age=18)
  328. # INFO:root:Created a Person object: Person(name='Myelsa', age=18)
1-2、VBA:
略,待后补。
2、推荐阅读:

2-1、Python-VBA函数之旅-open()函数

Python算法之旅:Algorithm

Python函数之旅:Functions 

个人主页:https://blog.csdn.net/ygb_1024?spm=1010.2135.3001.5421
文章知识点与官方知识档案匹配,可进一步学习相关知识
算法技能树首页概览60891 人正在系统学习中
遨游码海,我心飞扬
微信名片
注:本文转载自blog.csdn.net的神奇夜光杯的文章"https://myelsa1024.blog.csdn.net/article/details/138543121"。版权归原作者所有,此博客不拥有其著作权,亦不承担相应法律责任。如有侵权,请联系我们删除。
复制链接
复制链接
相关推荐
发表评论
登录后才能发表评论和回复 注册

/ 登录

评论记录:

未查询到任何数据!
回复评论:

分类栏目

后端 (14832) 前端 (14280) 移动开发 (3760) 编程语言 (3851) Java (3904) Python (3298) 人工智能 (10119) AIGC (2810) 大数据 (3499) 数据库 (3945) 数据结构与算法 (3757) 音视频 (2669) 云原生 (3145) 云平台 (2965) 前沿技术 (2993) 开源 (2160) 小程序 (2860) 运维 (2533) 服务器 (2698) 操作系统 (2325) 硬件开发 (2492) 嵌入式 (2955) 微软技术 (2769) 软件工程 (2056) 测试 (2865) 网络空间安全 (2948) 网络与通信 (2797) 用户体验设计 (2592) 学习和成长 (2593) 搜索 (2744) 开发工具 (7108) 游戏 (2829) HarmonyOS (2935) 区块链 (2782) 数学 (3112) 3C硬件 (2759) 资讯 (2909) Android (4709) iOS (1850) 代码人生 (3043) 阅读 (2841)

热门文章

101
推荐
关于我们 隐私政策 免责声明 联系我们
Copyright © 2020-2024 蚁人论坛 (iYenn.com) All Rights Reserved.
Scroll to Top