精华内容
下载资源
问答
  • zip() 是 Python 中最好用内置类型之一,它可以接收多个可迭代对象参数,再返回一个迭代器,可以把不同可迭代对象元素组合起来。我之前写迭代器系列时候,在《Python进阶:设计模式之迭代器模式》...

    zip() 是 Python 中最好用的内置类型之一,它可以接收多个可迭代对象参数,再返回一个迭代器,可以把不同可迭代对象的元素组合起来。

    我之前写迭代器系列的时候,在《Python进阶:设计模式之迭代器模式》(https://mp.weixin.qq.com/s/7MbRCn37fIIN42rLm6ho3g) 中简单地介绍过它,前几天翻译了 Python 3.10 采纳的 PEP-618 (https://mp.weixin.qq.com/s/W6XkRjDHvVSqtZKRceqwdw),介绍了它将会迎来的变更。

    但是,还有不少同学并不知道 zip(),或者不能熟练掌握它的用法,因此本文打算来做一个更为详细的梳理。

    内容主要分三部分:

    • 用法部分:介绍它的基础用法、高级用法、骚操作用法
    • 进阶部分:介绍它的实现原理,关注几个实现的细节
    • 发散部分:聚焦它的不足,以及解决方法

    1、zip() 的 n 种用法

    基本用法:像拉链一样,将多个可迭代对象组合起来,然后可以用 for 循环依次取出,或者一次性将结果存入列表、元组或者字典之类的容器中。

    f89484ea71719a70854d53922b6321d7.png

    它的结果是一个迭代器,迭代器生成的元素是元组,第 i 个元组的元素分别来自可迭代对象参数的第 i 个元素,如上图所示。

    另外,for 循环还可以把元组内的元素依次取出,这样会很方便:

    1bc7dd848f039338699c467cc7ca56df.png

    它的参数并不要求是同一类的可迭代对象,因此可以有非常多的组合方式,例如:

    abcba8e3ab91abd28a58736b3cd2ecd5.png

    但是,如果把字典作为 zip() 的参数,会是什么结果呢?字典是 key-value 键值对形式,跟列表之类的单一元素结构不同。

    实验一下,可以看出,zip() 默认只会遍历字典的 key 值:

    005fbed4291bdd5afc243262e819f654.png

    如果想要取出字典的 value 值,或者取出 key-value 键值对,那么可以使用字典自带的遍历方法 values() 和 items():

    920475c12ff96d146deac6e382dec8d0.png

    使用 zip(),还可以比较方便地对二维列表实现行列转换:

    4ecd7d5fde8b6e2a064c73d4614d2e08.png

    上例中的星号(*)操作符可以解包(unpacking),即将 my_list 的元素(也是列表)解成多个参数给 zip(),从而将 3 个列表重新组合。

    解包操作符对于 zip 对象同样适用,因为 zip() 本身是一次行列转换的操作,若将它解包后作为参数给 zip(),等于再做一次行列转换,也就是回到了原点(除了最后的结果是元组):

    7bcbe9dd274a146dcca5cb198932a487.png

    最后再介绍一种用法:创建 n*n 的方阵,每行的数字相同。

    1d04ee02ca10608dc94cf0be55868580.png

    2、zip() 的原理解析

    官方文档中给出了 zip() 的 Python 伪代码(并非是 Python 解释器内置的实现,只为了展示基本的代码逻辑):

    def zip(*iterables):    # zip('ABCD', 'xy') --> Ax By    sentinel = object()    iterators = [iter(it) for it in iterables]    while iterators:        result = []        for it in iterators:            elem = next(it, sentinel)            if elem is sentinel:                return            result.append(elem)        yield tuple(result)

    在这段简短的代码中,可以分析出几点关键的信息:

    • zip 接收可变数量的可迭代对象参数,这些参数会经过 iter() 处理成迭代器。推论:若出现非可迭代对象,此处会报错
    • while 循环在判断列表是否为空,而列表中的元素是将参数转化而成的迭代器。推论:若入参存在有效的可迭代对象,则 while 循环始终为真;若没有入参,则什么都不做
    • next() 会依次读取迭代器中的下一个元素,它的第二个参数会作为迭代器耗尽时的返回值。推论:每一轮依次取出这些迭代器的一个元素,当某个迭代被耗尽时,则退出死循环,这就意味着未耗尽的迭代器会被直接舍弃

    3、zip() 的问题与解决

    zip() 最明显的问题是它会舍弃掉未耗尽的迭代器:

    dbd937409ecec17ae8dd8769e73d7b62.png

    这是一种木桶效应,最终的结果由最短的木板来决定。

    有一种解决思路是取长板,同时补足短板(用 None 值填充),这就是 itertools 中的 zip_longest 方法:

    964832984f3735b47f71389c9c344813.png

    它填充了冗余数据,同时最大限度地保证了原始数据的完整性。

    但是,如果我们不希望有冗余数据,只希望得到按最长方式对齐的数据呢?

    Python 官方最近采纳了 PEP-618,它就是为了应对这个问题。当出现迭代器长度不一致时,它既不向短板妥协,也不向长板妥协,而是抛出 ValueError。它认为入参值错误,也就是严格要求入参的数据完整性。

    该 PEP 会被合入到一年后的 Python 3.10 版本,关于更多的内容细节,可查阅这篇PEP-618 译文 。(https://mp.weixin.qq.com/s/W6XkRjDHvVSqtZKRceqwdw)

    展开全文
  • 可变形参的函数

    2019-06-16 22:06:30
    可变形参的函数 总共有三种方式: initializer_list (c++11) 省略符形参 可变参数模板 (c++11) initializer_list 这种只适用于全部实参类型相同,我们可用initializer_list类型的形参. 注意initializer_list也是模板...

    可变形参的函数

    总共有三种方式:

    • initializer_list (c++11)
    • 省略符形参
    • 可变参数模板 (c++11)

    initializer_list

    这种只适用于全部实参类型相同,我们可用initializer_list类型的形参.
    注意initializer_list也是模板类型,但与vector不同的是,initializer_list中的元素值永远是常量值,我们无法去改变它的元素.
    例子:

    void error_msg(ErrorCode e, initializer_list<string> il)
    {
        cout<<e.msg()<<":";
        for(const auto &elem:il)
            cout<<elem<<" ";
        cout<<endl;
    }
    

    省略号形参

    这种方法是为了便于C++程序访问某些特殊C代码而设置的,这些C代码使用了varargs的C标准库功能.
    省略号形参应该仅仅用于C和C++通用的类型(基本类型),一般的类类型在传递给形参时都无法正确的拷贝.
    典型例子: printf(const char* format,...);
    声明:
    省略号形参只能出现在最后的一个形参.

    void func(param_list,...);
    void func(...);
    

    处理可变参数的标准宏:

    //可变参数标准宏头文件
    #include "stdarg.h"
     
    //申明va_list数据类型变量pvar,该变量访问变长参数列表中的参数。
    va_list pvar;
     
    //宏va_start初始化变长参数列表。pvar是va_list型变量,记载列表中的参数信息。
    //parmN是省略号"..."前的一个参数名,va_start根据此参数,判断参数列表的起始位置。
    va_start(pvar, parmN);
     
    //获取变长参数列表中参数的值。pvar是va_list型变量,type为参数值的类型,也是宏va_arg返回数值的类型。
    //宏va_arg执行完毕后自动更改对象pvar,将其指向下一个参数。
    va_arg(pvar, type);
     
    //关闭本次对变长参数列表的访问。
    va_end(pvar);
    

    例子:

    #include <stdarg.h>
    function (parmN, ...)
    {
     
    	va_list pvar; 
    	va_start (pvar, parmN);
    	while(...)
    	{
    		...
    			f = va_arg (pvar, type);
    		...
    	}
    	va_end (pvar);
    }
    

    补充:
    注意…形参入栈顺序,这和调用方式有关,请看我的另一篇博客.

    可变参数模板

    展开全文
  • 问题说明 我在使用JPA作为项目ORM框架...这样肯定是过滤掉了全部数据了。 疑问:为啥这里Hibernate会在SQL中 自动加上这个createTime=0 这个条件呢?很奇怪~~ 直到我看见 在这里实例化对象中, 对象createTi...

    问题说明

    我在使用JPA作为项目的ORM框架的时候,在分页查询中,不管咋样使用查询不出来数据,然后发现Hibernate构建的查询SQL中,在where子句中带上了createTime=0这个条件。这样肯定是过滤掉了全部数据了。
    在这里插入图片描述

    疑问:为啥这里Hibernate会在SQL中 自动加上这个createTime=0 这个条件呢?很奇怪~~

    直到我看见 在这里实例化的对象中,
    在这里插入图片描述

    对象的createTime属性我定义的是 int 这个基本数据类型。

    恍然大悟

    实例化对象的时候,基本数据类型都会有初始值的,比如这里的int初始值 不就是 0嘛,然后Hibernate 就会将对象中不为null的字段,都添加在where 后面作为条件。如下
    在这里插入图片描述

    解决:

    我把createTime字段的类型改为 包装类型interger 就可以了。

    然后,我把这个情况和我的小伙伴讲了,
    在这里插入图片描述
    在这里插入图片描述

    我又查了阿里巴巴开发规范,哎~~果真
    在这里插入图片描述

    特写此文,让我自己长记长性把!无奈自己比较菜,加油加油吧!

    展开全文
  • 如果实参数量未知,但全部实参类型相同,就可以使用initializer_list类型的形参(使用时需包含同名头文件) 定义initializer_list对象时,必须说明列表中所含元素的类型 例如 initializer_list<string>lst;/...

    C++有一种特殊的形参类型(即省略符),可以用它传递可变数量的形参,这种功能一般用于与C函数交互的接口程序。
    initializer_list 形参
    如果实参数量未知,但全部实参类型相同,就可以使用initializer_list类型的形参(使用时需包含同名头文件)

    定义initializer_list对象时,必须说明列表中所含元素的类型

    例如
    	initializer_list<string>lst;//initializer_list的元素是string类型
    	initializer_list<int>lst;
    

    initializer_list的元素都是常量值,无法改变

    #include<string>
    #include <iostream>
    #include<initializer_list>
    
    using namespace std;
    void error_msg(initializer_list<string>il)
    {
    	for (auto beg = il.begin(); beg != il.end(); ++beg) {
    		cout << *beg << " ";	
    	}
    	cout << endl;
    	
    }
    
    int main()
    {
    	string expected = "Hello", actual;
    	cin >> actual;
    	if (expected != actual) 
    	{
    		error_msg({ "functionX",expected,actual });//传入实参用{a,b,c}这种形式
    	}
    	else
    	{
    		error_msg({ "functionX","okay" });
    	}
    
    	system("pause");
    	return 0;
    }
    

    省略符形参

    void foo(parm_list, ...);
    //第一种形式为特定数目的形参提供了声明。在这种情况下,当函数被调用时,对于与显示声明的形参相对应的实参进行类型检查,而对于与省略符对应的实参则暂停类型检查。在第一钟形式中,形参声明后面的逗号是可选的。
    void foo(...);//第二种无需类型检查
    

    练习6.27

    #include <iostream>
    #include<initializer_list>
    using namespace std;
    int sum(initializer_list<int>il) {
    	int x = 0;
    	for (auto beg = il.begin(); beg != il.end(); ++beg) {
    		x += *beg;
    	}
    	return x;
    }
    int main()
    {
    	int a = sum({ 1,2,3,4,5 });
    	cout << a << endl;//结果15
    	system("pause");
    	return 0;
    }
    

    练习6.28
    for循环中的elem类型是const std::string&
    练习6.29
    取决于initializer_list元素的类型。当类型是内置类型时,引用是不必要的。因为内置类型复制起来很容易(比如int)。否则,使用引用(const)是更好的选择。

    展开全文
  • 为了编写能处理不同数量实参函数,C++提供了两种主要方法: 一.如果所有实参类型相同,可以传递一个名为initializer_list标准库... 如果函数实参数量未知但是全部实参的类型相同,我们可以使用initializer
  • C++可变形实现

    2021-03-09 22:30:54
    如果函数实参数量未知但是全部实参的类型相同,可以使用initializer_list类型的形参。 initializer_list是标准库类型,定义在<initializer_list>头文件中,用于表示某种特定类型的数组。 支持操作: ...
  • 其形式如下:#define 宏名称 替换文本宏宏和函数区别如下:宏做是简单字符串替换(注意是字符串替换,不是其他类型参数替换),而函数参数传递,参数是有数据类型的,可以是各种各样的类型;宏的参...
  • c# 值类型实例构造器

    2020-12-25 22:25:35
    只能定义有构造器,并且构造器中必须为值类型所有字段全部赋值,否则报错。 c#中虽然没有无构造器,但是可以使用这个语法初始化在内部字段: StructType st = new StructType();//为内部字段初始化0或者...
  • 这篇文章将会带你全部弄懂Kotlin泛型中reified实化类型参数,包括它基本使用、源码原理、以及使用场景。有了上篇文章介绍,相信大家对kotlinreified实化类型参数有了一定认识和了解。那么这篇文章将会更加...
  • 展开全部直接定义a=True/False就行,来示例代码:源#定义布尔bai值类型duzhi数a,b,值分别为daoTrue,Falsea=Trueb=Falseprinta,bprinttype(a),type(b)>>>True FalsePython中布尔类型:Python布尔类型...
  • 为了编写能够处理不同数量形参函数,C++11提供了两种主要方法: 如果所有形参的类型相同,可以传递一个名为initializer_list标准库类型 如果形参的类型不同,可以使用...如果函数形参数量未知但全部形参...
  • 易错点:1、如果不在学生对象中重写toString方法,那么在集合中就会出现,遍历出来后arr{i}全部都是引用对象地址,并不是对象。2、引用数据类型与基本数据类型最大区别,引用数据类型要事先定义好各项属性与...
  • 类型实例构造器

    2012-10-16 16:14:00
    CLR总是允许创建值类型的实例。另外值类型不一定需要定义构造器,c#编译器不会为值类型生成默认构造...只能定义有构造器,并且构造器中必须为值类型所有字段全部赋值,否则报错。c#中虽然没有无构造器...
  • 如果你写了一个包含N个参数多参数构造方法,当创建实例时候,是不是特别谨慎在大脑里记着第几个参数是给哪个属性赋值,生怕给弄错了,当然类型不对时候,编译器还会友善提醒赋值错了,但对那些类型相同...
  • 展开全部当Java中函数中,想要实现output parameter时,对应62616964757a686964616fe58685e5aeb931333363356466参数,不能是Immutable,即不能是,不可更改,而String就是Immutable,所以要换用StringBuilder之...
  • PHP7标量类型声明RFC

    2015-09-02 10:14:31
    一、总结 该RFC建议添加4种新的标量类型声明:int,float...),让同一个PHP文件内的全部函数调用和语句返回,都有一个“严格约束”的标量类型声明检查。此外,在开启严格类型约束后,调用拓展或者PHP内置函数在
  • javax.sql.rowset.serial 提供实用工具类,允许 SQL 类型与 Java 编程语言数据类型之间可序列化映射关系。 javax.sql.rowset.spi 第三方供应商在其同步提供者实现中必须使用标准类和接口。 javax.swing 提供...
  • 提出疑问在Go源码库或者其他开源项目中,会发现有些函数在需要用到切片入时,它采用是指向切片类型的指针,而非切片类型。这里未免会产生疑问:切片底层不就是指针指向底层数组数据吗,为何不直接传递切片,两者...
  • elasticsearch搜索类型简介

    千次阅读 2015-07-11 16:19:23
    我们尝试一个最简单搜索全部员工请求: GET /megacorp/employee/_search 接下来,让我们搜索姓氏中包含“jake”员工。要做到这一点,我们将在命令行中使用轻量级搜索方法。这种方法常被称作查询字符串(query...
  • '**************************************************'函数ID:0041[生成随机密码]'函数名:MakeRndPass'作 用:生成随机密码' 数:passlen ---- 要生成密码长度' 数:passtype ---- 要生成密码类型'返回值...
  • '**************************************************'''''函数ID:0028[取得图像的类型|宽|高]'函数名:GetImageDx'作 用:取得图像的类型|宽|高' 数:filepath ---- 文件路径及文件命名'返回值:"类型|宽|高"'*...
  • 这个demo的file入参的类型是MultipartFile,很多网上的例子是File类型。这两个类型在解析文件的时候还是有点区别的。 第①个方法: [url=][/url]1 /**2 * 这个deomo入参的类型是MultipartFile,很多网上的例子是...
  • Gomarshal unmarshal

    千次阅读 2019-08-27 16:45:02
    :返回数据为结果和错误 结果为[]byte []uint8类型 全部都是数字, 使用os.Stdout.Write(b)将ascii转化为字符 unmarshal:将[]byte转化为任意我们规定的类型:第一个参数是我们输入数据,类型是[]byte ...
  • 且构造方法要求严格,每一个类中至少有一个构造方法,如果没有,系统会默认创建一个构造方法,而且是无参的,如果个人自己创建的构造方法全部是有参的构造方法,程序将会报错。 二、什么是封装? 答:封装在我个人...
  • 其形式如下:#define 宏名称 替换文本宏宏和函数区别如下:宏做是简单字符串替换(注意是字符串替换,不是其他类型参数替换),而函数参数传递,参数是有数据类型的,可以是各种各样的类型;宏的参...
  • ## 构造方法——JavaSE零基础 一、构造方法 1、作用是用于初始化参数。...三、如果自己写了有参的构造方法,那么编辑器不会在提供默认的构造方法了,如果我们还想用无参的构造方法,那么需要...
  • 第七季主要是给大家介绍一下Java面向对象中继承,包括:继承概念、为什么要继承、继承的类型及特性、extends关键字、final关键字、implements关键字、super和this关键字、子类中如何调用父类中、无构造...
  • 1.StringBuffer或者StringBuilder 创建时候,如果是无构造(),会直接在底层创建一个长度为16char类型数组;如果是有构造(string),会在参数基础上加上16。推荐使用(int)构造,会直接生成一个确定容量...

空空如也

空空如也

1 2 3 4 5 ... 10
收藏数 186
精华内容 74
关键字:

参的全部类型