1.代码是源码正什么意思?
2.main() { int i=5,j; j=(++i)+((++i)+(++i)+(++i))*2; printf("%d %d\n",i,j); }
3.OpenOffice其他社区
4.二维码有哪些基本知识?
代码是什么意思?
代码 含意
0 0x 作业完成。
1 0x 不正确的源码正函数。
2 0x 系统找不到指定的源码正档案。
3 0x 系统找不到指定的源码正路径。
4 0x 系统无法开启档案。源码正
5 0x 拒绝存取。源码正资金版指标源码
6 0x 无效的源码正代码。
7 0x 储存体控制区块已毁。源码正
8 0x 储存体空间不足,源码正无法处理这个指令。源码正
9 0x 储存体控制区块地址无效。源码正
0xA 环境不正确。源码正
0xB 尝试加载一个格式错误的源码正程序。
0xC 存取码错误。源码正
0xD 资料错误。源码正
0xE 储存体空间不够,无法完成这项作业。
0xF 系统找不到指定的磁盘驱动器。
0x 无法移除目录。
0x 无法移除目录。
0x 系统无法将档案移到 其它的磁盘驱动器。
0x 没有任何档案。
0x 储存媒体为写保护状态。
0x 系统找不到指定的装置。
0x 装置尚未就绪。
0x 装置无法识别指令。
0x 资料错误 (cyclic redundancy check)
0x 程序发出一个长度错误的指令。
0x 磁盘驱动器在磁盘找不到 持定的扇区或磁道。
0xA 指定的磁盘或磁盘无法存取。
0xB 磁盘驱动器找不到要求的扇区。
0xC 打印机没有纸。
0xD 系统无法将资料写入指定的磁盘驱动器。
0xE 系统无法读取指定的装置。
0xF 连接到系统的某个装置没有作用。
0x The process cannot access the file because it is being
used by another process.
0x 档案的一部份被锁定, 现在无法存取。
0x 磁盘驱动器的磁盘不正确。 请将 %2 (Volume Serial
Number: %3) 插入磁盘机%1。
0x 开启的分享档案数量太多。
0x 到达档案结尾。
0x 磁盘已满。
0x 不支持这种网络要求。
0x 远程计算机无法使用。
0x 网络名称重复。
0x 网络路径找不到。
0x 网络忙碌中。
0x The specified network resource or device is no longer
available.
0x The network BIOS command limit has been reached.
0x 网络配接卡发生问题。
0xA 指定的服务器无法执行要求的作业。
0xB 网络发生意外错误。
0xC 远程配接卡不兼容。
0xD 打印机队列已满。
0xE 服务器的空间无法储存等候打印的档案。
0xF 等候打印的档案已经删除。
0x 指定的网络名称无法使用。
0x 拒绝存取网络。
0x 拒绝存取网络。
0x 网络资源类型错误。
0x 网络名称找不到。
0x 超过区域计算机网络配接卡的名称限制。
0x 超过网络 BIOS 作业阶段的限制。
0x 远程服务器已经暂停或者正在起始中。
0x 由于联机数目已达上限,此时无法再联机到这台远程计算机。
0x 指定的打印机或磁盘装置已经暂停作用。
0x 档案已经存在。
0x 无法建立目录或档案。
0x INT 0x 处理这项要求的储存体无法使用。
0x 近端装置名称已经在使用中。
0x 指定的网络密码错误。
0x 参数错误。
0x 网络发生资料写入错误。
0x 此时系统无法执行其它行程。双币对冲源码
0x 无法建立其它的系统 semaphore。
0x 属于其它行程专用的 semaphore.
0x semaphore 已经设定,而且无法关闭。
0x 无法指定 semaphore 。
0x 在岔断时间无法要求专用的 semaphore 。
0x 在岔断时间无法要求专用的 semaphore 。
0x 此 semaphore 先前的拥有权已经结束。
0xA 请将磁盘插入 %1。
0xB 因为代用的磁盘尚未插入,所以程序已经停止。
0xC 磁盘正在使用中或被锁定。
0xD Pipe 已经中止。
0xE 系统无法开启指定的 装置或档案。
0xF 档名太长。
0x 磁盘空间不足。
0x 没有可用的内部档案标识符。
0x 目标内部档案标识符不正确。
0x 由应用程序所执行的 IOCTL 呼叫 不正确。
0x 写入验证参数值不正确。
0x 系统不支持所要求的指令。
0x 此项功能仅在 Win 模式有效
0x semaphore 超过逾时期间。
0xA 传到系统呼叫的资料区域 太小。
0xB 文件名、目录名称或储存体卷标语法错误。
0xC 系统呼叫层次不正确。
0xD 磁盘没有设定卷标。
0xE 找不到指定的模块。
0xF 找不到指定的程序。
0x 没有子行程可供等待。
0x 没有子行程可供等待。
0x %1 这个应用程序无法在 Win 模式下执行。
0x Attempt to use a file handle to an open disk
partition for an operation other than raw disk I/O.
0x 尝试将档案指针移至档案开头之前。
0x 无法在指定的装置或档案,设定档案指针。
0x JOIN 或 SUBST 指令 无法用于 内含事先结合过的磁盘驱动器。
0x 尝试在已经结合的磁盘驱动器,使用 JOIN 或 SUBST 指令。
0x 尝试在已经替换的磁盘驱动器,使 用 JOIN 或 SUBST 指令。
0x 系统尝试删除 未连结过的磁盘驱动器的连结关系。
0xA 系统尝试将磁盘驱动器结合到已经结合过之磁盘驱动器的目录。
0xB 系统尝试将磁盘驱动器替换成已经替换过之磁盘驱动器的目录。
0xC 系统尝试将磁盘驱动器替换成已经替换过之磁盘驱动器的目录。
0x 系统尝试将磁盘驱动器 SUBST 成已结合的磁盘驱动器 目录。
0xE 系统此刻无法执行 JOIN 或 SUBST。
0xF 系统无法将磁盘驱动器结合或替换同一磁盘驱动器下目录。
0x 这个目录不是根目录的子目录。
0x 目录仍有资料。
0x 指定的路径已经被替换过。
0x 资源不足,无法处理这项 指令。
0x 指定的路径这时候无法使用。
0x 指定的路径这时候无法使用。
0x 尝试要结合或替换的磁盘驱动器目录,是已经替换过的的目标。
0x CONFIG.SYS 文件未指定系统追踪信息,或是追踪功能被取消。
0x 指定的 semaphore事件 DosMuxSemWait 数目不正确。
0x DosMuxSemWait 没有执行;设定太多的 semaphore。
0x DosMuxSemWait 清单不正确。
0xA 您所输入的储存媒体标 元长度限制。
0xB 无法建立其它的执行绪。
0xC 接收行程拒绝接受信号。
0xD 区段已经被舍弃,无法被锁定。
0xE 区段已经解除锁定。
0xF 执行绪识别码的地址不正确。
0xA0 传到 DosExecPgm 的自变量字符串不正确。
0xA1 指定的路径不正确。
0xA2 信号等候处理。
0xA4 系统无法建立执行绪。微社区 系统源码
0xA7 无法锁定档案的部份范围。
0xAA 所要求的资源正在使用中。
0xAD 取消范围的锁定要求不明显。
0xAE 档案系统不支持自动变更锁定类型。
0xB4 系统发现不正确的区段号码。
0xB6 操作系统无法执行 %1。
0xB6 操作系统无法执行 %1。
0xB7 档案已存在,无法建立同一档案。
0xBA 传送的旗号错误。
0xBB 指定的系统旗号找不到。
0xBC 操作系统无法执行 %1。
0xBD 操作系统无法执行 %1。
0xBE 操作系统无法执行 %1
0xBF 无法在 Win 模式下执行 %1。
0xC0 操作系统无法执行 %1。
0xC1 %1 不是正确的 Win 应用程序。
0xC2 操作系统无法执行 %1。
0xC3 操作系统无法执行 %1。
0xC4 操作系统无法执行 这个应用程序。
0xC5 操作系统目前无法执行 这个应用程序。
0xC6 操作系统无法执行 %1。
0xC7 操作系统无法执行 这个应用程序。
0xC8 程序代码的区段不可以大于或等于 KB。
0xC9 操作系统无法执行 %1。
0xCA 操作系统无法执行 %1。
0xCB 系统找不到输入的环境选项。\r
0xCD 在指令子目录下,没有任何行程有信号副处理程序。
0xCE 文件名称或扩展名太长。
0xCF ring 2 堆栈使用中。
0xCF ring 2 堆栈使用中。
0xD0 输入的通用档名字元 * 或 ? 不正确, 或指定太多的通用档名字元。
0xD1 所传送的信号不正确。
0xD2 无法设定信号处理程序。
0xD4 区段被锁定,而且无法重新配置。
0xD6 附加到此程序或动态连结模块的动态连结模块太多。
0xD7 Can’t nest calls to LoadModule.
0xE6 The pipe state is invalid.
0xE7 所有的 pipe instances 都在忙碌中。
0xE8 The pipe is being closed.
0xE9 No process is on the other end of the pipe.
0xEA 有更多可用的资料。
0xF0 作业阶段被取消。
0xFE 指定的延伸属性名称无效。
0xFF 延伸的属性不一致。
0x 没有可用的资料。
0xA 无法使用 Copy API。
0xB 目录名称错误。
0x 延伸属性不适用于缓冲区。
0x 在外挂的档案系统上的延伸属性档案已经毁损。
0x 延伸属性表格文件满。
0x 指定的延伸属性代码无效。
0x 指定的延伸属性代码无效。
0xA 外挂的这个档案系统不支持延伸属性。
0x 意图释放不属于叫用者的 mutex。
0xA semaphore 传送次数过多。
0xB 只完成 Read/WriteProcessMemory 的部份要求。
0xD 系统找不到位于讯息文件 %2 中编号为 0x%1 的讯息。
0xE7 尝试存取无效的地址。
0x 运算结果超过 位。
0x 信道的另一端有一个行程在接送资料。
0x 等候行程来开启信道的另一端。
0xE2 存取延伸的属性被拒。
0xE3 由于执行绪结束或应用程序要求,而异常终止 I/O 作业。
0xE4 重叠的 I/O 事件不是设定成通知状态。
0xE5 正在处理重叠的 I/O 作业。
0xE6 对内存位置的无效存取。
0xE7 执行 inpage 作业发生错误。
0xE9 递归太深,堆栈满溢。
0xEA 窗口无法用来传送讯息。
0xEB 无法完成这项功能。注册工具源码下载
0xEC 旗号无效。
0xED 储存媒体未含任何可辨识的档案系统。 请确定以加载所需
的系统驱动程序,而且该储存媒体并未毁损。
0xEE 储存该档案的外部媒体发出警告,表示该已开启档案已经无效。
0xEF 所要求的作业无法在全屏幕模式下执行。
0xF0 An attempt was made to reference a token that does
not exist.
0xF1 组态系统登录数据库毁损。
0xF2 组态系统登录机码无效。
0xF3 无法开启组态系统登录机码。
0xF4 无法读取组态系统登录机码。
0xF5 无法写入组态系统登录机码。
0xF6 系统登录数据库中的一个档案必须使用记录或其它备份还
原。 已经还原成功。
0xF7 系统登录毁损。其中某个档案毁损、或者该档案的 系统映
对内存内容毁损、会是档案无法复原。
0xF8 系统登录起始的 I/O 作业发生无法复原的错误。 系统登录
无法读入、写出或更新,其中的一个档案 内含系统登录在内存中的内容。
0xF9 系统尝试将档案加载系统登录或将档案还原到系统登录中,
但是,指定档案的格式不是系统登录文件的格式。
0xFA 尝试在标示为删除的系统登录机码,执行不合法的操作。
0xFA 尝试在标示为删除的系统登录机码,执行不合法的操作。
0xFB 系统无法配置系统登录记录所需的空间。
0xFC 无法在已经有子机码或数值的系统登录机码建立符号连结。
0xFD 无法在临时机码下建立永久的子机码。
0xFE 变更要求的通知完成,但信息 并未透过呼叫者的缓冲区传
回。呼叫者现在需要自行列举档案,找出变更的地方。
0xB 停止控制已经传送给其它服务 所依峙的一个服务。
0xC 要求的控制对此服务无效
0xF8 系统登录起始的 I/O 作业发生无法复原的错误。 系统登录
无法读入、写出或更新,其中的一个档案 内含系统登录在内存中的内容。
0xF9 系统尝试将档案加载系统登录或将档案还原到系统登录中,
但是,指定档案的格式不是系统登录文件的格式。
0xFA 尝试在标示为删除的系统登录机码,执行不合法的操作。
0xFA 尝试在标示为删除的系统登录机码,执行不合法的操作。
0xFB 系统无法配置系统登录记录所需的空间。
0xFC 无法在已经有子机码或数值的系统登录机码建立符号连结。
0xFD 无法在临时机码下建立永久的子机码。
0xFE 变更要求的通知完成,但信息 并未透过呼叫者的缓冲区传
回。呼叫者现在需要自行列举档案,找出变更的地方。
0xB 停止控制已经传送给其它服务 所依峙的一个服务。
0xC 要求的控制对此服务无效
0xC 要求的控制对此服务无效
0xD The service did not respond to the start or control
request in a timely fashion. 0xE 无法建立服务的执行绪。
0xF 服务数据库被锁定。
0x 这种服务已经在执行。
0x 帐户名称错误或者不存在。
0x 指定的服务暂停作用,无法激活。
0x 指定循环服务从属关系。
0x 指定的服务不是安装进来的服务。
0x 该服务项目此时无法接收控制讯息。
0x 服务尚未激活。
0x 无法联机到服务控制程序。
0x 处理控制要求时,发生意外状况。
0x 指定的数据库不存在。
0xA 服务传回专属于服务的ip测速网站源码错误码。
0xB The process terminated unexpectedly.
0xC 从属服务或群组无法激活。
0xD 因为登入失败,所以没有激活服务。
0xE 在激活之后,服务在激活状态时当机。
0xF 指定服务数据库锁定无效。
0x 指定的服务已经标示为删除。
0x 指定的服务已经存在。
0x 系统目前正以上一次执行成功的组态执行。
0x 从属服务不存在,或已经标示为删除。
0x 目前的激活已经接受上一次执行成功的 控制设定。
0x 上一次激活之后,就没有再激活服务。
0x 指定的名称已经用于服务名称或服务显示 名称。
0xC 已经到了磁带的最后。
0xD 到了档案标示。
0xE 遇到磁带的开头或分割区。
0xC 已经到了磁带的最后。
0xD 到了档案标示。
0xE 遇到磁带的开头或分割区。
0xF 到了档案组的结尾。
0x 磁带没有任何资料。
0x 磁带无法制作分割区。
0x 存取多重容体的新磁带时,发现目前 区块大小错误。
0x 加载磁带时,找不到磁带分割区信息。
0x 无法锁住储存媒体退带功能。
0x 无法锁住储存媒体退带功能。
0x 无法解除加载储存媒体。
0x 磁盘驱动器中的储存媒体已经变更。
0x 已经重设 I/O 总线。
0x 磁盘驱动器没有任何储存媒体。
0x 目标 multi-byte code page,没有对应 Unicode 字符。
0xA 动态链接库 (DLL) 起始例程失败。
0xB 系统正在关机。
0xC 无法中止系统关机,因为没有关机的动作在进行中。
0xD 因为 I/O 装置发生错误,所以无法执行要求。
0xE 序列装置起始失败,会取消加载序列驱动程序。
0xF 无法开启装置。这个装置与其它装置共享岔断要求 (IRQ)。
至少已经有一个使用同一IRQ 的其它装置已经开启。
0x A serial I/O operation was completed by another
write to the serial port. (The IOCTL_SERIAL_XOFF_COUNTER reached zero.)
0x 因为已经过了逾时时间,所以序列 I/O 作业完成。
(IOCTL_SERIAL_XOFF_COUNTER 不是零。)
0x 在磁盘找不到任何的 ID 地址标示。
0x 磁盘扇区 ID 字段与磁盘控制卡追踪地址 不符。
0x 软式磁盘驱动器控制卡回报了一个软式磁盘驱动器驱动程序无法识别的错误。
0x 软式磁盘驱动器控制卡传回与缓存器中不一致的结果。
0x 存取硬盘失败,重试后也无法作业。
0x 存取硬盘失败,重试后也无法作业。
0x 存取硬盘时,必须重设磁盘控制卡,但是 连重设的动作也失败。
0x 到了磁带的最后。
0xA 可用服务器储存空间不足,无法处理这项指令。
0xB 发现潜在的死锁条件。
0xC 指定的基本地址或档案位移没有适当 对齐。
0x 尝试变更系统电源状态,但其它的应用程序或驱动程序拒绝。
0x 系统 BIOS 无法变更系统电源状态。
0xE 指定的程序需要新的 Windows 版本。
0xF 指定的程序不是 Windows 或 MS-DOS 程序。
0x 指定的程序已经激活,无法再激活一次。
0x 指定的程序是为旧版的 Windows 所写的。
0x 执行此应用程序所需的链接库档案之一毁损。
0x 没有应用程序与此项作业的指定档案建立关联。
0x 传送指令到应用程序发生错误。
0x 找不到执行此应用程序所需的链接库档案。
0xB0 指定的装置名称无效。
0xB1 装置现在虽然未联机,但是它是一个记忆联机。
0xB2 尝试记忆已经记住的装置。
0xB3 提供的网络路径找不到任何网络提供程序。
0xB3 提供的网络路径找不到任何网络提供程序。
0xB4 指定的网络提供程序名称错误。
0xB5 无法开启网络联机设定文件。
0xB6 网络联机设定文件坏掉。
0xB7 无法列举非容器。
0xB8 发生延伸的错误。
0xB9 指定的群组名称错误。
0xBA 指定的计算机名称错误。
0xBB 指定的事件名称错误。
0xBC 指定的网络名称错误。
0xBD 指定的服务名称错误。
0xBE 指定的网络名称错误。
0xBF 指定的资源共享名称错误。
0xC0 指定的密码错误。
0xC1 指定的讯息名称错误。
0xC2 指定的讯息目的地错误。
0xC3 所提供的条件与现有的条件组发生冲突。
0xC4 尝试与网络服务器联机,但是 与该服务器的联机已经太多。
0xC5 其它网络计算机已经在使用这个工作群组或网域名称。
main() { int i=5,j; j=(++i)+((++i)+(++i)+(++i))*2; printf("%d %d\n",i,j); }
PSï¼ä¸ºäºè§£è°ï¼ä¸é¨ä¸è½½äºVC6.0ï¼çµèä¸åVSå²çªï¼åæ¢äºå°çµèæè£ ä¸ã
æµè¯äºä¸ä¸ï¼ç¡®å®é®é¢å¾å¤§ï¼release模å¼ç»æj=ï¼debug模å¼ç»æj=
â为ä»ä¹çäºï¼å¯¹debug模å¼çexeåç¼è¯ï¼åç°è¿ç®é¡ºåºä¸æ£å¸¸ï¼æ¬å·éå ç®ä¸åï¼åè·³åºå»æ§è¡å¦ä¸ä¸ªæ¬å·ï¼åè·³åæ¥ç®å¦ä¸åæ¬å·ï¼é常é常åæï¼
ä¸ãå 计ç®++i;++i;++i;
äºæ¯ï¼è¡¨è¾¾å¼åæ(++i)+(i+i+i)*2
äºãåç®i+i;
äºæ¯ï¼è¡¨è¾¾å¼åæ(++i)+(+i)*2
ä¸ãå计ç®++i;
ç»æï¼è¡¨è¾¾å¼åæj=9+(8+8+9)*2=ï¼
âåæ±ç¼ä»£ç å¦ä¸ï¼å·²ç®åï¼ç¨iåjåéçèµ·æ¥ç´è§ï¼
mov [i], 5
mov [j], 0
mov eax, [i] //eax=5ï¼è®¡ç®++i
add eax, 1 //eax=6
mov [i], eax //i=6
mov ecx, [i] //ecx=6ï¼è®¡ç®++i
add ecx, 1 //ecx=7
mov [i], ecx //i=7
mov edx, [i] //edx=7ï¼è®¡ç®++i
add edx, 1 //edx=8
mov [i], edx //i=8
mov eax, [i] //eax=8ï¼è®¡ç®8+8
add eax, [i] //eax=8+i=
mov ecx, [i] //ecx=8ï¼è®¡ç®++i
add ecx, 1 //ecx=9
mov [i], ecx //i=9
add eax, [i] //eax=+9=ï¼æ³¨æï¼i+i+iæ¯æä¹åæ8+8+9ç
mov edx, [i] //edx=i=9
lea eax, [edx+eax*2]//eax=9+*2=
mov [j], eax //j=
mov ecx, [j]
push ecx
mov edx, [i]
push edx
push offset Format ; "=%d,j=%d\n"
call _prntf
ææ³ï¼æ们å°åºæ¯ä¸ºäºç 究Cè¯è¨å¢ï¼è¿æ¯è¦ç 究ç¼è¯å¨ï¼æè§è¿ç§æºä»£ç ä¸æ¯ç¨æ¥é 读çï¼èæ¯ç¨æ¥è§£è°ã å³å®äºï¼ä»¥åå¦ä¹ Cè¯è¨åå³æå¼++æä½ç¬¦ã
éï¼æèé¢ï¼VC++6.0çdebug模å¼ä¸ï¼å¨i=5çåæä¸ï¼ä¸ºä»ä¹
j = (++i) + (++i) + (i++) + (i++); // j =
j = (i++) + (i++) + (++i) + (++i); // j =
j = (i++) + (++i) + (i++) + (++i); // j =
OpenOffice其他社区
全球众多开源社区之所以能够进行交流,是因为它们都认同开放源码软件的基本理念。作为三大开源社区之一,OpenOffice org社区在开源软件领域获得了广泛关注与支持,并与其他开源社区建立了密切的合作关系。以下是其中一些合作案例: Mozilla社区与OpenOffice org合作开发插件,以实现在Mozilla浏览器中的应用。Apache社区提供了优秀的XML/XSLT软件,并在POI项目中与OpenOffice org合作将MS Excel文件格式文档化。Cocoon项目及其子项目Forrest在服务器端将OpenOffice org无缝集成进内容管理系统,实现了与服务器端的高效协同。OpenGroupware社区与OpenOffice org群件项目协作,提供邮件、日志、即时消息和白板等功能,客户端软件Glow正在开发中。CPAN社区的OpenOffice::OODoc项目支持Perl对OpenOffice org文档的访问。Zope/Plone社区用Python实现了内容管理系统/架构,OpenFlow以此为基础实现了工作流管理系统,这些软件现在都已成为流行的开源软件。Zope中所包含的CMFOODocument和ZooDocument支持对OpenOffice org文档的访问,使得OpenOffice org可以作为内容著作工具集成进内容管理系统。基于Zope/Plone的软件商icoya提供了包含OpenOffice org的内容管理解决方案。国内也有一些与Zope/Plone相关的社区,如Python中文社区、Zope/Plone中文社区、中文Zope用户组、中蟒(中文Python)等。 OpenOffice org及其相关的开源社区相互协调、共同发展,为个人消费者和团体用户提供了更优秀的软件及整体解决方案。在办公自动化、电子出版、工作流、内容管理等领域,OpenOffice org及其解决方案的应用前景广阔。 关于OpenOffice对中文的支持,软件提供了中日韩文字支持,但中文输入法的支持存在一些缺点。在Word中输入中文标点符号后保存,再次打开文档时,标点可能被误识别为超链接。对于使用OpenOffice的中文用户来说,这可能是一个需要改进的地方,希望OpenOffice能够在未来得到进一步的完善。扩展资料
OpenOffice.org 是一套跨平台的办公室软件套件,能在 Windows、Linux、MacOS X (X)、和 Solaris 等操作系统上执行。它与各个主要的办公室软件套件兼容。OpenOffice.org 是自由软件,任何人都可以免费下载、使用、及推广它。二维码有哪些基本知识?
基础知识
首先,我们先说一下二维码一共有个尺寸。官方叫版本Version。Version 1是 x 的矩阵,Version 2是 x 的矩阵,Version 3是的尺寸,每增加一个version,就会增加4的尺寸,公式是:(V-1)*4 + (V是版本号) 最高Version ,(-1)*4+ = ,所以最高是 x 的正方形。
下面我们看看一个二维码的样例:
定位图案
Position Detection Pattern是定位图案,用于标记二维码的矩形大小。这三个定位图案有白边叫Separators for Postion Detection Patterns。之所以三个而不是四个意思就是三个就可以标识一个矩形了。
Timing Patterns也是用于定位的。原因是二维码有种尺寸,尺寸过大了后需要有根标准线,不然扫描的时候可能会扫歪了。
Alignment Patterns 只有Version 2以上(包括Version2)的二维码需要这个东东,同样是为了定位用的。
功能性数据
Format Information 存在于所有的尺寸中,用于存放一些格式化数据的。
Version Information 在 >= Version 7以上,需要预留两块3 x 6的区域存放一些版本信息。
数据码和纠错码
除了上述的那些地方,剩下的地方存放 Data Code 数据码 和 Error Correction Code 纠错码。
数据编码
我们先来说说数据编码。QR码支持如下的编码:
Numeric mode 数字编码,从0到9。如果需要编码的数字的个数不是3的倍数,那么,最后剩下的1或2位数会被转成4或7bits,则其它的每3位数字会被编成 ,,bits,编成多长还要看二维码的尺寸(下面有一个表Table 3说明了这点)
Alphanumeric mode 字符编码。包括 0-9,大写的A到Z(没有小写),以及符号$ % * + – . / : 包括空格。这些字符会映射成一个字符索引表。如下所示:(其中的SP是空格,Char是字符,Value是其索引值) 编码的过程是把字符两两分组,然后转成下表的进制,然后转成bits的二进制,如果最后有一个落单的,那就转成6bits的二进制。而编码模式和字符的个数需要根据不同的Version尺寸编成9, 或个二进制(如下表中Table 3)
Byte mode, 字节编码,可以是0-的ISO--1字符。有些二维码的扫描器可以自动检测是否是UTF-8的编码。
Kanji mode 这是日文编码,也是双字节编码。同样,也可以用于中文编码。日文和汉字的编码会减去一个值。如:在0X to 0X9FFC中的字符会减去,在0XE到0XEBBF中的字符要减去0XC,然后把结果前两个进制位拿出来乘以0XC0,然后再加上后两个进制位,最后转成bit的编码。如下图示例:
Extended Channel Interpretation (ECI) mode 主要用于特殊的字符集。并不是所有的扫描器都支持这种编码。
Structured Append mode 用于混合编码,也就是说,这个二维码中包含了多种编码格式。
FNC1 mode 这种编码方式主要是给一些特殊的工业或行业用的。比如GS1条形码之类的。
简单起见,后面三种不会在本文 中讨论。
下面两张表中,
Table 2 是各个编码格式的“编号”,这个东西要写在Format Information中。注:中文是
Table 3 表示了,不同版本(尺寸)的二维码,对于,数字,字符,字节和Kanji模式下,对于单个编码的2进制的位数。(在二维码的规格说明书中,有各种各样的编码规范表,后面还会提到)
下面我们看几个示例,
示例一:数字编码
在Version 1的尺寸下,纠错级别为H的情况下,编码:
1. 把上述数字分成三组:
2. 把他们转成二进制: 转成 ; 转成 ; 转成 。
3. 把这三个二进制串起来:
4. 把数字的个数转成二进制 (version 1-H是 bits ): 8个数字的二进制是
5. 把数字编码的标志和第4步的编码加到前面:
示例二:字符编码
在Version 1的尺寸下,纠错级别为H的情况下,编码: AC-
1. 从字符索引表中找到 AC- 这五个字条的索引 (,,,4,2)
2. 两两分组: (,) (,4) (2)
3.把每一组转成bits的二进制:
(,) *+ 等于 转成 (,4) *+4 等于 转成 (2) 等于 2 转成
4. 把这些二进制连接起来:
5. 把字符的个数转成二进制 (Version 1-H为9 bits ): 5个字符,5转成
6. 在头上加上编码标识 和第5步的个数编码:
结束符和补齐符
假如我们有个HELLO WORLD的字符串要编码,根据上面的示例二,我们可以得到下面的编码,
编码
字符数
HELLO WORLD的编码
我们还要加上结束符:
编码
字符数
HELLO WORLD的编码
结束
按8bits重排
如果所有的编码加起来不是8个倍数我们还要在后面加上足够的0,比如上面一共有个bits,所以,我们还要加上2个0,然后按8个bits分好组:
补齐码(Padding Bytes)
最后,如果如果还没有达到我们最大的bits数的限制,我们还要加一些补齐码(Padding Bytes),Padding Bytes就是重复下面的两个bytes: (这两个二进制转成十进制是和,我也不知道为什么,只知道Spec上是这么写的)关于每一个Version的每一种纠错级别的最大Bits限制,可以参看QR Code Spec的第页到页的Table-7一表。
假设我们需要编码的是Version 1的Q纠错级,那么,其最大需要个bits,而我们上面只有个bits,所以,还需要补个bits,也就是需要3个Padding Bytes,我们就添加三个,于是得到下面的编码:
上面的编码就是数据码了,叫Data Codewords,每一个8bits叫一个codeword,我们还要对这些数据码加上纠错信息。
纠错码
上面我们说到了一些纠错级别,Error Correction Code Level,二维码中有四种级别的纠错,这就是为什么二维码有残缺还能扫出来,也就是为什么有人在二维码的中心位置加入图标。
错误修正容量
L水平 7%的字码可被修正
M水平 %的字码可被修正
Q水平 %的字码可被修正
H水平 %的字码可被修正
那么,QR是怎么对数据码加上纠错码的?首先,我们需要对数据码进行分组,也就是分成不同的Block,然后对各个Block进行纠错编码,对于如何分组,我们可以查看QR Code Spec的第页到页的Table-到Table-的定义表。注意最后两列:
Number of Error Code Correction Blocks :需要分多少个块。
Error Correction Code Per Blocks:每一个块中的code个数,所谓的code的个数,也就是有多少个8bits的字节。
举个例子:上述的Version 5 + Q纠错级:需要4个Blocks(2个Blocks为一组,共两组),头一组的两个Blocks中各个bits数据 + 各 9个bits的纠错码(注:表中的codewords就是一个8bits的byte)(再注:最后一例中的(c, k, r )的公式为:c = k + 2 * r,因为后脚注解释了:纠错码的容量小于纠错码的一半)
下图给一个5-Q的示例(因为二进制写起来会让表格太大,所以,我都用了十进制,我们可以看到每一块的纠错码有个codewords,也就是个8bits的二进制数)
组
块
数据
对每个块的纠错码
1 1 6 6
2 7 7 6
2 1 7 6 7
2 6 5 2
注:二维码的纠错码主要是通过Reed-Solomon error correction(里德-所罗门纠错算法)来实现的。对于这个算法,对于我来说是相当的复杂,里面有很多的数学计算,比如:多项式除法,把1-的数映射成2的n次方(0<=n<=)的伽罗瓦域Galois Field之类的神一样的东西,以及基于这些基础的纠错数学公式,因为我的数据基础差,对于我来说太过复杂,所以我一时半会儿还有点没搞明白,还在学习中,所以,我在这里就不展开说这些东西了。还请大家见谅了。(当然,如果有朋友很明白,也繁请教教我)
最终编码
穿插放置
如果你以为我们可以开始画图,你就错了。二维码的混乱技术还没有玩完,它还要把数据码和纠错码的各个codewords交替放在一起。如何交替呢,规则如下:
对于数据码:把每个块的第一个codewords先拿出来按顺度排列好,然后再取第一块的第二个,如此类推。如:上述示例中的Data Codewords如下:
块 1 6 6
块 2 7 7 6
块 3 7 6 7
块 4 6
我们先取第一列的:, , ,
然后再取第二列的:, , , , ,, ,
如此类推:, , , , ,, , ……… ……… ,,6,,,7,
对于纠错码,也是一样:
块 1
块 2
块 3
块 4 5 2
和数据码取的一样,得到:,,,,,,,,…… …… ,,,
然后,再把这两组放在一起(纠错码放在数据码之后)得到:
, , , , , , , , , , , , , 7, , , , , , , , , 7, 6, , , , , , 7, , , , , , , , , , , 6, , , , , , 6, , 6, , , , , , , , , 6, , , 7, , , , , , , , , , , , , 5, , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , , 2, , , , , , , , , , , , , , , ,
这就是我们的数据区。
Remainder Bits
最后再加上Reminder Bits,对于某些Version的QR,上面的还不够长度,还要加上Remainder Bits,比如:上述的5Q版的二维码,还要加上7个bits,Remainder Bits加零就好了。关于哪些Version需要多少个Remainder bit,可以参看QR Code Spec的第页的Table-1的定义表。
画二维码图
Position Detection Pattern
首先,先把Position Detection图案画在三个角上。(无论Version如何,这个图案的尺寸就是这么大)
Alignment Pattern
然后,再把Alignment图案画上(无论Version如何,这个图案的尺寸就是这么大)
关于Alignment的位置,可以查看QR Code Spec的第页的Table-E.1的定义表(下表是不完全表格)
下图是根据上述表格中的Version8的一个例子(6,,)
Timing Pattern
接下来是Timing Pattern的线(这个不用多说了)
Format Information
再接下来是Formation Information,下图中的蓝色部分。
Format Information是一个个bits的信息,每一个bit的位置如下图所示:(注意图中的Dark Module,那是永远出现的)
这个bits中包括:
5个数据bits:其中,2个bits用于表示使用什么样的Error Correction Level, 3个bits表示使用什么样的Mask
个纠错bits。主要通过BCH Code来计算
然后个bits还要与做XOR操作。这样就保证不会因为我们选用了的纠错级别和的Mask,从而造成全部为白色,这会增加我们的扫描器的图像识别的困难。
下面是一个示例:
关于Error Correction Level如下表所示:
关于Mask图案如后面的Table 所示。
Version Information
再接下来是Version Information(版本7以后需要这个编码),下图中的蓝色部分。
Version Information一共是个bits,其中包括6个bits的版本号以及个bits的纠错码,下面是一个示例:
而其填充位置如下:
数据和数据纠错码
然后是填接我们的最终编码,最终编码的填充方式如下:从左下角开始沿着红线填我们的各个bits,1是黑色,0是白色。如果遇到了上面的非数据区,则绕开或跳过。
掩码图案
这样下来,我们的图就填好了,但是,也许那些点并不均衡,如果出现大面积的空白或黑块,会告诉我们扫描识别的困难。所以,我们还要做Masking操作(靠,还嫌不复杂)QR的Spec中说了,QR有8个Mask你可以使用,如下所示:其中,各个mask的公式在各个图下面。所谓mask,说白了,就是和上面生成的图做XOR操作。Mask只会和数据区进行XOR,不会影响功能区。(注:选择一个合适的Mask也是有算法的)
其Mask的标识码如下所示:(其中的i,j分别对应于上图的x,y)
下面是Mask后的一些样子,我们可以看到被某些Mask XOR了的数据变得比较零散了。
Mask过后的二维码就成最终的图了。
好了,大家可以去尝试去写一下QR的编码程序,当然,你可以用网上找个Reed Soloman的纠错算法的库,或是看看别人的源代码是怎么实现这个繁锁的编码。
2024-11-25 19:19
2024-11-25 19:18
2024-11-25 18:46
2024-11-25 17:42
2024-11-25 17:34
2024-11-25 17:05