python jpg 简单研究 1

news2024/11/25 4:06:20

起因, 目的:

就是想看看 jpg 里面有什么。
其实,我最开始的想法是,自己来写一个文件格式,只能我自己才能打开。
然后看了 jpg 相关的内容,发现太复杂,只能罢了。

1. jpg 的魔法头数字(File Magic Numbers : ff d8 ff e0

验证一下是不是 jpg
def main(filename):
    print(f"filename: {filename}")

    with open(filename, 'rb') as file:
        first_4_bytes = file.read(4)
        print(first_4_bytes)
        magic_numbers = first_4_bytes.hex()

    print(f"magic numbers: {magic_numbers}")
    return magic_numbers

if __name__ == "__main__":
    main("bt1.jpg")
    
# 输出
# filename: bt1.jpg
# b'\xff\xd8\xff\xe0'
# magic numbers: ffd8ffe0
2. 搞点小动作。
  1. 先在一个 jpg 文件的文件头部, 添加一些字节,产生一个新的文件,X?
  2. 这个 X 就会产生 : Windows照片查看器无法显示此图片
  3. 然后从文件头删除这些添加的字节, 把 X 还原为 jpg.

def modify_jpg(input_file, output_file):
    """
    在JPG文件的文件头添加指定的字节

    :param input_file: 输入文件的路径
    :param output_file: 输出文件的路径
    :param bytes_to_add: 要添加的字节
    """
    bytes_to_add = b'\x01\x02\x03\x04'

    with open(input_file, 'rb') as f:
        file_content = f.read()

    # 在文件头添加字节
    modified_content = bytes_to_add + file_content

    with open(output_file, 'wb') as f:
        f.write(modified_content)
    print(f"File '{output_file}' has been created with the added bytes.")


def restore_jpg(modified_file, original_file):
    """
    从修改后的JPG文件头删除之前添加的字节,还原JPG文件
    :param modified_file: 被修改的文件路径
    :param original_file: 要写入还原后文件的路径
    """
    with open(modified_file, 'rb') as f:
        file_content = f.read()

    # 检查文件内容是否以添加的字节开始
    if file_content.startswith(b'\x01\x02\x03\x04'):
        # 删除文件头的字节
        restored_content = file_content[4:]
    else:
        print("The file does not start with the expected bytes.")
        return

    with open(original_file, 'wb') as f:
        f.write(restored_content)
    print(f"File '{original_file}' has been restored.")

# 使用示例
input_path = 'bt1.jpg'  # 原始JPG文件路径
modified_path = 'modified.jpg'  # 修改后的文件路径
restored_path = 'restored.jpg'  # 还原后的文件路径

# 第一步:修改JPG文件
modify_jpg(input_path, modified_path)

# 第二步:还原JPG文件
restore_jpg(modified_path, restored_path)

结论 + todo

有时候,一时的想法, 不知从何而起,以为很简单,其实很费劲。


老哥留步,支持一下。

请求支持

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/2194704.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

蝶形激光器驱动(温控精度0.002°C 激光电流分辨率5uA)

蝶形半导体激光器驱动电流的稳定性直接决定了其输出波长的稳定性,进而影响检测精度.为了满足气体浓度检测中对激光器输出波长稳定可调的要求,设计了数字与模拟电路混合的恒流驱动电路.STM32为主控芯片数控模块完成扫描AD/DA转换;模拟电路主要由负反馈运算放大、高精度CMOS管和反…

《向量数据库指南》揭秘:Mlivus Cloud如何借Fivetran Partner SDK实现数据飞跃

哈哈,各位向量数据库领域的同仁们,今天咱们来聊聊 Fivetran 的 Partner SDK 如何助力技术供应商构建自定义连接器和目标,特别是与 Mlivus Cloud 的集成,这可是个热门话题啊! Fivetran 的 Partner SDK,简直就是为技术供应商量身打造的“神器”。有了它,你就可以轻松地为…

LeetCode讲解篇之300. 最长递增子序列

文章目录 题目描述题解思路题解代码题目链接 题目描述 题解思路 这题我们可以通过动态规划求解&#xff0c;使用一个数组f&#xff0c;数组f的i号元素表示[0, i]范围内最长递增子序列的长度 状态转移方程&#xff1a;f[i] max(f[j] 1)&#xff0c;其中 0 < j < i 题…

node高版本报错: digital envelope routines::unsupported

node高版本报错&#xff1a; digital envelope routines::unsupported 解决方案&#xff1a; package.json中&#xff0c;启动命令前加上&#xff1a; set NODE_OPTIONS--openssl-legacy-provider &&

Windows安装Linux子系统报错:WslRegisterDistribution failed with error: 0x8007019e

WslRegisterDistribution failed with error: 0x8007019e 报错截图如下图&#xff1a; 该处是由于没有安装Linux内核&#xff0c;因此需要安装。可前往官网查看详情&#xff1a;https://aka.ms/wslinstall 需要解决该问题&#xff0c;可参照官网方法&#xff08;我没试过官网…

pip丢了怎么办!不用怕,教你用get-pip.py来下载

1.下载get-pip.py进行安装 我们有的时候环境中会找不到或者误删丢失了pip模块&#xff0c;就没办法安装新的python模组&#xff0c;那怎么办呢&#xff0c;官方提供了get-pip.py模块可以帮我们快速安装pip。 get-pip.py网站 bootstrap.pypa.io/get-pip.py 直接将文件下载下来…

已解决:AttributeError: ‘str‘ object has no attribute ‘decode‘

已解决&#xff1a;AttributeError: ‘str’ object has no attribute ‘decode’ 文章目录 写在前面问题描述报错原因分析 解决思路解决办法1. 确保只对 bytes 对象调用 decode()2. 将 Python 2 的旧代码迁移到 Python 33. 检查数据来源4. 处理编码不一致的问题5. 使用 six 库…

Java第二阶段---11封装---第四节 static 修饰符

1.static 修饰符应用范围 static修饰符只能用来修饰类中定义的成员变量、成员方法、代码块以及内部类(内部类有专门章节进行讲解)。 2.static 修饰成员变量 static 修饰的成员变量称之为类变量。属于该类所有成员共享。 示例 package cn.lyxq.test04;public class Chinese…

系统架构设计师论文《论企业应用系统的分层架构风格》精选试读

论文真题 软件架构风格是描述一类特定应用领域中系统组织方式的惯用模式&#xff0c;反映了领域中诸多系统所共有的结构特征和语义特征&#xff0c;并指导如何将各个模块和子系统有效组织成一个完整的系统。分层架构是一种常见的软件架构风格&#xff0c;能够有效简化设计&…

HDLBits中文版,标准参考答案 | 3.1.3 Arithmetic Circuits | 算术电路

关注 望森FPGA 查看更多FPGA资讯 这是望森的第 10 期分享 作者 | 望森 来源 | 望森FPGA 目录 1 Half adder | 半加器 2 Full adder | 全加器 3 3-bit binary adder | 3位二进制加法器 4 Adder | 加法器 5 Signed addition overflow | 有符号数的加法溢出 6 100-bit bi…

【JavaEE初阶】深入理解线程池的概念以及Java标准库提供的方法参数分析

前言 &#x1f31f;&#x1f31f;本期讲解关于MySQL索引事务&#xff0c;希望能帮到屏幕前的你。 &#x1f308;上期博客在这里&#xff1a;【JavaEE初阶】多线程案列之定时器的使用和内部原码模拟-CSDN博客 &#x1f308;感兴趣的小伙伴看一看小编主页&#xff1a;GGBondlctrl…

ScholarAI发一个月会员啦!

诸神缄默不语-个人CSDN博文目录 ScholarAI是一个用于学术的工具&#xff0c;用LLM智能检索用户所需的论文&#xff0c;可以进行简单的总结和分析。可以理解成“LLM帮你读论文”这种感觉。 这次之所以发会员是因为GPT Store服务出问题了&#xff0c;所以给了用户一个月会员作为…

双向数据库迁移工具:轻松实现 MySQL 与 SQLite 数据互导

项目概述与作用 该项目的核心是实现 MySQL 和 SQLite 两种数据库之间的数据迁移工具。它能够轻松地将 MySQL 数据库中的数据导出为 SQLite 数据库文件&#xff0c;反过来也可以将 SQLite 数据库中的数据上传到 MySQL 数据库中。这个双向迁移工具非常适用于&#xff1a; 数据库备…

【C++】--类和对象(2)

&#x1f44c;个人主页: 起名字真南 &#x1f446;个人专栏:【数据结构初阶】 【C语言】 【C】 目录 1 类的默认成员函数2 构造函数3 析构函数4 拷贝构造5 赋值运算符重载5.1 运算符重载5.2 赋值运算符的重载 1 类的默认成员函数 默认成员函数就是用户没有显示实现&#xff0c;…

制作U盘启动盘1 — UltraISO

官网&#xff1a;UltraISO软碟通中文官方网站 - 光盘映像文件制作/编辑/转换工具 点击工具栏的“打开”&#xff0c;在弹出的窗口选择要刻录的ISO文件。 点击菜单栏的“启动”—“写入磁盘映像”。 硬盘驱动器选择要刻录的U盘。 点击写入&#xff0c;会弹出数据丢失的提示&…

数据结构和算法简介

目录 1.认识数据结构 什么是数据结构 逻辑结构 物理结构 常见的数据结构 2.认识算法 什么是算法 如何衡量算法效率 时间复杂度 什么是时间复杂度 如何计算时间复杂度 大O渐进表示法 常见时间复杂度计算例子 空间复杂度 什么是空间复杂度 如何计算空间复杂度 常…

【数据结构】深度解析堆排序

目录 &#x1f4af;引言 &#x1f4af;堆的概念 &#xff08;一&#xff09;什么是堆 &#xff08;二&#xff09;堆的表示 &#x1f4af;堆排序原理 &#xff08;一&#xff09;建堆 &#xff08;二&#xff09;排序 &#x1f4af;代码实现 &#x1f4af;代码分析 &…

【Sqlite】sqlite内部函数sqlite3_value_text特性

目录 ⚛️1 结论 ☪️2 说明 ☪️3 传入数值转成科学计数法 ♋3.1 只有整数部分 ♏3.2 只有小数部分 ♐3.3 整数小数 ⚛️1 结论 整数(sqlite视为int64)位数 > 20位&#xff0c;sqlite3_value_text 采用科学计数法。否则正常表示。 浮点数(sqlite视为double)的整数部…

STM32 通用同步/异步通信

一、串行通信简介 CPU与外围设备之间的信息交换称为通信。基本的通信方式有并行通信和串行通信两种。STM32单片机提供了功能强大的串行通信模块&#xff0c;即通用同步/异步收发器&#xff08;USART&#xff09;。 1.串行通信 串行通信是数据字节一位一位地依次传送的通信方式。…

HarmonyOS第一课 05 从简单的页面开始-习题

【习题】从简单的页面开始 通过/及格分80/ 满分100 判断题 1.Button作为容器使用时可以通过添加子组件实现包含文字、图片等元素的按钮&#xff0c;其类型包括胶囊按钮、圆形按钮、普通按钮。T 正确(True) 错误(False) 大部分前端框架的按钮都具有这几个类型,鸿蒙也不例外…