小编rv.*_*tch的帖子

如何类型提示 __getattr__ 方法的返回类型?

我很好奇Python 3 中是否有一种方法可以提示__getattr__()Python 中方法的返回类型。

我有以下用于测试目的的虚拟代码:

class MyClass:

    def __getattr__(self, item: str) -> str:
        return 'test'

    def __getattribute__(self, item: str) -> str:
        return 'test'


c = MyClass()

print(c.hello, type(c.hello))  # test <class 'str'>
Run Code Online (Sandbox Code Playgroud)

不幸的是,Pycharm 无法解析hello上面的属性类型。我不确定,但我认为它目前是按Any类型处理的。

我还对上述代码提出了以下变体,但仍然无法使类型提示按预期工作:

from typing import Callable

ReturnsString = Callable[[], str]


class MyClass:

    my_test_fn: ReturnsString = lambda self: 'hello'
    __getattr__: ReturnsString = lambda self, _item: 'test'
    __getattribute__: ReturnsString


c = MyClass()

# type hinting works as expected - return type is `str` …
Run Code Online (Sandbox Code Playgroud)

python getattr python-3.x python-typing

11
推荐指数
0
解决办法
2708
查看次数

如何从 Python 中的方法启用字典的代码完成?

我正在将 Python 3.6 与 PyCharm 一起使用,但令人沮丧的是,对于字典对象的特殊情况(具有固定键模式),不支持代码完成。

举例来说,我创建并尝试访问一个简单的字典对象,如下所示:

inventory = {'name': 'hammer', 'price': 2.3}
inventory['']
Run Code Online (Sandbox Code Playgroud)

当我将光标放在引号“ ”内并点击时,Ctrl + Space我会完成代码,并且 IDE 会正确建议字典对象中的所有可能的键。那太棒了

但是,如果我尝试将其构建为返回相同字典对象的实用程序函数,例如使用用户提供的值但使用相同的字典键 - 那么我将不再获得代码完成!

def get_inventory(name: str, price: float):
    return {'name': name, 'price': price}

inventory = get_inventory('hammer', 2.3)
inventory['']    # <- Pycharm can't offer any suggestions! 
Run Code Online (Sandbox Code Playgroud)

有什么解决方法或解决方案吗?我已经搜索过类似的解决方案,但没有找到任何有效的解决方案。我知道我可以将其转换为一个类Inventory并以这种方式访问​​属性,但我不想这样做,原因如下:

  • 我需要该对象能够轻松地进行 JSON 转换,因为我可能会经常将其从 JSON 传递到 JSON,而dict对象是实现此目的最简单的方法
  • 将其存储为类没有多大意义,因为无论如何我只需要它作为数据容器,其中存储的属性最少

任何关于如何让我的 IDE 通过识别此类对象中可能的键来协助代码完成的帮助或解决方案dict将不胜感激!

python autocomplete code-completion pycharm python-3.x

7
推荐指数
2
解决办法
8362
查看次数

如何在 Python 3.6 中将 ForwardRef 作为参数传递给 TypeVar?

我正在开发一个当前支持Python 3.6+ 的库,但在如何在 Python 3.6 的模块中定义前向引用方面遇到了一些麻烦typing。我已经pyenv在本地 Windows 计算机上进行了设置,以便可以轻松地在不同的 Python 版本之间切换以进行本地测试,因为我的系统解释器默认为 Python 3.9。

这里的用例本质上是我尝试使用TypeVar有效的前向引用类型定义 a ,然后我可以将其用于类型注释目的。我已经确认当我在 3.7+ 上并直接从模块导入时,以下代码运行没有问题,但我无法在 Python 3.6 上获取它,因为我注意到前向引用不能用作某些参数原因。我还尝试将前向引用类型作为参数传递给,但遇到了类似的问题。ForwardReftypingTypeVarUnion

TypeVar以下是我试图在 python 3.6.0 以及更新版本(如 3.6.8)上工作的导入和定义- 我确实注意到我在次要版本之间遇到了不同的错误:

from typing import _ForwardRef as PyForwardRef, TypeVar


# Errors on PY 3.6:
#   3.6.2+ -> AttributeError: type object '_ForwardRef' has no attribute '_gorg'
#   3.6.2 or earlier -> AssertionError: assert isinstance(a, GenericMeta)
FREF = TypeVar('FREF', str, PyForwardRef)
Run Code Online (Sandbox Code Playgroud)

下面是我已经测试过的示例用法,它似乎按照 Python …

python type-hinting forward-declaration python-3.x python-typing

7
推荐指数
1
解决办法
3227
查看次数

正则表达式匹配“|” 联合类型的分隔值

我正在尝试匹配类型注释,例如int | str,并使用正则表达式替换将它们替换为 string Union[int, str]

期望的替换(之前和之后):

  • str|int|bool->Union[str,int,bool]
  • Optional[int|tuple[str|int]]->Optional[Union[int,tuple[Union[str,int]]]]
  • dict[str | int, list[B | C | Optional[D]]]->dict[Union[str,int], list[Union[B,C,Optional[D]]]]

到目前为止我想出的正则表达式如下:

r"\w*(?:\[|,|^)[\t ]*((?'type'[a-zA-Z0-9_.\[\]]+)(?:[\t ]*\|[\t ]*(?&type))+)(?:\]|,|$)"
Run Code Online (Sandbox Code Playgroud)

您可以在 Regex Demo 上尝试一下。它并没有真正按照我想要的方式工作。到目前为止我注意到的问题:

  • 到目前为止,它似乎无法处理嵌套的 Union 条件。例如,int | tuple[str|int] | bool似乎会导致一场匹配,而不是两次匹配(包括内部 Union 条件)。

  • 正则表达式似乎]最后消耗了不必要的东西。

  • 可能是最重要的一个,但我注意到 Python 中的模块似乎不支持正则表达式子例程re是我想到使用它的地方。

附加信息

这主要是为了支持Python 3.7+ 的PEP 604语法,该语法需要前向声明(例如声明为字符串)注释才能支持,否则内置类型不支持该|运算符。

这是我想出的示例代码:

r"\w*(?:\[|,|^)[\t ]*((?'type'[a-zA-Z0-9_.\[\]]+)(?:[\t ]*\|[\t ]*(?&type))+)(?:\]|,|$)"
Run Code Online (Sandbox Code Playgroud)

对于 3.10 之前的 Python 版本,我使用__future__import 来避免出现以下错误: …

python regex annotations python-3.x python-typing

5
推荐指数
1
解决办法
946
查看次数

我如何输入提示初始化参数与数据类中的字段相同?

假设我有一个自定义用例,我需要动态创建或定义__init__数据类的方法。

例如,假设我需要像这样装饰它,@dataclass(init=False)然后修改__init__()方法以采用关键字参数,例如**kwargs. 但是,在kwargs对象中,我仅检查已知数据类字段是否存在,并相应地设置这些属性(下面的示例)

我想向我的 IDE (PyCharm) 键入提示,修改后的内容__init__仅接受列出的数据类字段作为参数或关键字参数。我不确定是否有办法解决这个问题,使用typing库或其他方式。我知道 PY3.11 已计划进行数据类转换,这可能会也可能不会满足我的要求(我的直觉是否定的)。

这是我正在使用的示例代码,这是一个基本案例,说明了我遇到的问题:

from dataclasses import dataclass


# get value from input source (can be a file or anything else)
def get_value_from_src(_name: str, tp: type):
    return tp()  # dummy value


@dataclass
class MyClass:
    foo: str
    apple: int

    def __init__(self, **kwargs):
        for name, tp in self.__annotations__.items():
            if name in kwargs:
                value = kwargs[name]
            else:
                # here …
Run Code Online (Sandbox Code Playgroud)

python python-dataclasses python-typing

4
推荐指数
1
解决办法
1647
查看次数

检查 chrono::DateTime&lt;Utc&gt; 是否在日期和时间范围内的惯用方法?

我很好奇是否有一种惯用的方法来检查 a 是否chrono::DateTime<Utc>在时间范围内。在我的用例中,我只需要检查是否DateTime在当前时间的接下来的半小时内发生。

这是我到目前为止整理的内容。它使用timestamp()属性来获取我可以使用的原始(unix)时间戳。

use chrono::prelude::*;
use chrono::Duration;

#[inline(always)]
pub fn in_next_half_hour(input_dt: DateTime<Utc>) -> bool {
    in_future_range(input_dt, 30 * 60)
}

/// Check if a `DateTime` occurs within the following X seconds from now.
pub fn in_future_range(input_dt: DateTime<Utc>, range_seconds: i64) -> bool {
    let utc_now_ts = Utc::now().timestamp();
    let input_ts = input_dt.timestamp();

    let within_range = input_ts > utc_now_ts && input_ts <= utc_now_ts + range_seconds;

    within_range
}
Run Code Online (Sandbox Code Playgroud)

我的测试用例是这样的:

fn main() {
    let utc_now = Utc::now();

    let …
Run Code Online (Sandbox Code Playgroud)

datetime rust rust-chrono

3
推荐指数
1
解决办法
2637
查看次数

出于测试目的对函数调用进行计时的最简单方法是什么?

所以我对 Rust 还很陌生,但来自 Python 的我发现这种情况总体来说非常令人困惑。

我喜欢 Python,因为如果你想对一段代码或只是一个函数调用进行计时,它非常容易:

print(timeit('a = "hee hee la le dah"; my_awesome_fn()', number = 1_000, globals=globals()))
Run Code Online (Sandbox Code Playgroud)

然后只需调用python script.py,或者更好的是,只需使用 IDE 中的绿色“运行”按钮即可调用脚本。但我在 Rust 中找不到等效的功能。

我知道 Rust 生态系统中有一个称为基准测试的概念,并且有一些类似的库就是criterion为此目的而存在的。问题是我对高等数学和统计学一无所知(本质上可以把我当作一个无能的白痴),而且我怀疑我能否从这样的框架或工具中受益匪浅。

所以我只是好奇如何tests在 Cargo 中使用来测试 Rust 中的代码块,甚至更好,甚至是函数调用。

例如,假设我在 Rust 中有类似的函数,我想多次调用它,然后检查性能如何变化等:

pub fn my_awesome_fn() {
    trace!("getting ready to do something cool...");
    std::thread::sleep(std::time::Duration::from_millis(500));
    info!("finished!");
}
Run Code Online (Sandbox Code Playgroud)

我怎样才能简单地在 Rust 中计时这个函数my_awesome_fn?我想我正在寻找类似timeitpython 或类似的东西。理想情况下,它应该是直接使用的,并假设我对我正在做的事情一无所知。我很好奇是否有一个现有的库或框架可以用于此目的。

time performance-testing timeit rust

2
推荐指数
1
解决办法
4635
查看次数

从字符串中修剪多余空格的理想方法是什么?

我正在处理需要 用单个空格替换多个空格的字符串 。看起来其中大多数只是人为错误,但我对处理此问题的理想方法感到好奇 - 最好是从&str到 的分配最少String

到目前为止,这是我的方法如下:

const SPACE: &str = " ";
const TWO_SPACES: &str = "  ";

/// Replace multiple spaces with a single space
pub fn trim_whitespace(s: &str) -> String {
    let mut new_str: String = s.trim().to_owned();
    while new_str.contains(TWO_SPACES) {
        new_str = new_str.replace(TWO_SPACES, SPACE);
    }
    new_str
}

let result = trim_whitespace("Hello     world! ");
assert_eq!(result, "Hello world!");
Run Code Online (Sandbox Code Playgroud)

编辑(10/2022):我有Python背景,做上面这样的事情是非常惯用的。例如, Python 中最快的版本(用单个空格替换多个空格)似乎是这样的:

const SPACE: &str = " ";
const TWO_SPACES: &str = " …
Run Code Online (Sandbox Code Playgroud)

string whitespace replace rust

1
推荐指数
1
解决办法
5358
查看次数

对该方法中的参数类型感到困惑

我试图理解这段代码是如何工作的,我们有:

people = ['Dr. Christopher Brooks', 'Dr. Kevyn Collins-Thompson',
          'Dr. VG Vinod Vydiswaran', 'Dr. Daniel Romero']

def split_title_and_name(person):

    return person.split()[0] + ' ' + person.split()[-1]
Run Code Online (Sandbox Code Playgroud)

所以我们得到了一个列表,这个方法应该基本上删除“Dr.”之间的所有内容。和姓氏。据我所知, split() 函数不能用于列表,而是用于字符串。所以 person 必须是一个字符串。但是,我们还向 person 添加了 [0] 和 [-1],这意味着我们应该获取“person”的第一个和最后一个字符,但我们得到的是第一个单词和最后一个单词。我无法理解这段代码!你能帮我理解一下吗?

非常感谢任何帮助,谢谢:)

python string syntax list python-3.x

0
推荐指数
1
解决办法
79
查看次数