检查一个对象是否支持缓冲协议python

时间:2015-05-03 18:52:36

标签: python

我正在寻找Python C-API PyObject_CheckBuffer的等价物。

即。我想检查一个对象是否支持缓冲区协议,但是来自Python。

2 个答案:

答案 0 :(得分:11)

我认为你应该使用标准的试一试,看看它是否有效的技术:

$query1 = "INSERT INTO knine_parent_db
          SET usr = :usr,
              ClassIDOne = :ClassIDOne,
              ClassIDTwo = :ClassIDTwo,
              ClassIDThree = :ClassIDThree,
              ClassIDFour = :ClassIDFour,
              ClassIDFive = :ClassIDFive
          ";

$exec1 = [
    ':usr' => $_SESSION["usr"],
    ':ClassIDOne' => $_POST["cidone"],
    ':ClassIDTwo' => $_POST["cidtwo"],
    ':ClassIDThree' => $_POST["cidthree"],
    ':ClassIDFour' => $_POST["cidfour"],
    ':ClassIDFive' => $_POST["cidfive"],
];

$query2 = "UPDATE knine_settings_login
           SET ClassID = :usr
           WHERE usr = :usr
          ";

$exec2 = [':usr' => $_SESSION["usr"]];

$db_host = 'localhost';
$db_name = 'MyDatabase';
$db_user = 'user';
$db_pass = 'password';

$dsn = 'mysql:host='.$db_host.';dbname='.$db_name.';charset=utf8';

try
{
    $PDO = new PDO($dsn, $db_user, $db_pass);
}
catch(PDOException $e)
{
    // if dev mode
    echo 'Database connection error : ' . $e->getMessage();

    // if prod mode
    //header('Location: /404.html');
    //exit;
}

// begin of transaction
$PDO->beginTransaction();

$res1 = $PDO->prepare($query1);
$res2 = $PDO->prepare($query2);

if($res1->execute($exec1) && $res2->execute($exec2))
{
    $PDO->commit();
}
else
{
    $PDO->rollBack();
}

// end of transaction

答案 1 :(得分:1)

使用性能关键代码上的简短数据片段,我不得不尝试不同的方法。根据您的应用程序,一个可能会比其他更好。

def ensure_bytes__try(data):
    try:
        # memoryview used only for testing type; 'with' releases the view instantly
        with memoryview(data):
            return data
    except TypeError:
        return data.encode()

def ensure_bytes__isinstance(data):
    # Explicitly test for some bytes-like types
    # - misses array.array, numpy.array and all other types not listed here
    return data if isinstance(data, (bytes, bytearray, memoryview)) else data.encode()

def ensure_bytes__hasattr(data):
    # Works as long as your bytes-like doesn't have 'encode'
    return data.encode() if hasattr(data, "encode") else data

def ensure_bytes__args(data=None, data_bytes=None):
    # Avoid autodetection by using explicit arguments
    return data_bytes if data is None else data.encode()

以下基准显示了Python 3.7.4上每个实现所花费的时间:

ensure_bytes__try(b"foo")             ▒▒▒▒█████████████████ 438 ns
ensure_bytes__try("foo")              ▒▒▒▒▒██████████████████████████████████ 797 ns
ensure_bytes__isinstance(b"foo")      ▒▒▒▒█████████ 277 ns
ensure_bytes__isinstance("foo")       ▒▒▒▒▒███████████████████ 489 ns
ensure_bytes__hasattr(b"foo")         ▒▒▒▒████ 171 ns
ensure_bytes__hasattr("foo")          ▒▒▒▒▒█████████ 287 ns
ensure_bytes__args(data_bytes=b"foo") ▒▒▒▒██ 121 ns
ensure_bytes__args(data="foo")        ▒▒▒▒▒█████ 216 ns

缩短栏意味着更快。每个条形图的阴影部分代表以ref_bytes(b"foo")(84 ns)和ref_str("foo")(100 ns)为基准的参考时间:

def ref_bytes(data): return data
def ref_str(data): return data.encode()