热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

如何从ImageIO中排除特定的TIFF阅读器?

如何从ImageIO中排除特

这里的问题是ImageIO使用服务提供商接口(SPI)查找在运行时注册插件,并且在您的设置中找到了多个可以读取TIFF的插件。默认情况下,这些插件没有特定的顺序,这就是为什么有时您首先获得com.sun(JAI)TIFF插件,而有时首先获得it.geosolutions(Geosolutions)TIFF插件的原因。ImageIO.read(...)只会尝试第一个插件,如果失败则放弃。

如果可以的话,最简单的解决方案是从类路径中删除其中一个插件。但是我想你已经想到了这一点。还有许多其他方法可以解决此问题(我用Java给出了代码示例,因为这是我最熟悉的示例,因此我相信您可以在Scala中将其编写得更优雅;-)。

需要对代码进行最少更改的一种方法是在运行时注销“引导”代码中某处的JAI提供程序(确切的位置取决于应用程序,可能是静态初始化程序块或Web上下文侦听器,或者类似)。该IIORegistry有一个deregisterServiceProvider用于此目的的方法,去除从注册表中供应商,使其不能用于ImageIO

另一种选择是为提供者定义明确的顺序。如果出于某种原因(第三方要求/插件间的依存关系等)需要以单一格式拥有多个提供程序,这将很有用。该IIORegistry有一个setOrdering用于此目的,即允许设置方法成对 两个服务提供商的排序,使得ImageIO总是喜欢一个先于另一个。

下面的代码显示了以上两个选项:

// Get the global registry
IIORegistry registry = IIORegistry.getDefaultInstance();
// Lookup the known TIFF providers
ImageReaderSpi jaiProvider = lookupProviderByName(registry, "com.sun.media.imageioimpl.plugins.tiff.TIFFImageReaderSpi");
ImageReaderSpi geoProvider = lookupProviderByName(registry, "it.geosolutions.imageioimpl.plugins.tiff.TIFFImageReaderSpi");
if (jaiProvider != null && geoProvider != null) {
// If both are found, EITHER
// order the it.geosolutions provider BEFORE the com.sun (JAI) provider
registry.setOrdering(ImageReaderSpi.class, geoProvider, jaiProvider);
// OR
// un-register the JAI provider
registry.deregisterServiceProvider(jaiProvider);
}


// New and improved (shorter) version. :-)
private static T lookupProviderByName(final ServiceRegistry registry, final String providerClassname) {
try {
return (T) registry.getServiceProviderByClass(Class.forName(providerClassname));
}
catch (ClassnotFoundException ignore) {
return null;
}
}

上面的代码将确保Geosolutions
TIFF插件将始终由所使用ImageIO.read(...),并且您现有的代码应该可以正常工作(但现在很稳定)。

一个完全不同的选择是尝试使用所有已注册的TIFF插件读取数据,并使用第一个成功的插件。这比以前的代码更明确,但是需要重写图像读取代码:

byte[] data;
BufferedImage image;
try (ImageInputStream inputStream = ImageIO.createImageInputStream(new ByteArrayInputStream(data))) {
Iterator readers = ImageIO.getImageReaders(inputStream);
// Try reading the data, using each reader until we succeed (or have no more readers)
while (readers.hasnext()) {
ImageReader reader = readers.next();
try {
reader.setInput(inputStream);
image = reader.read(0);
break; // Image is now correctly decoded
}
catch (Exception e) {
// TODO: Log exception?
e.printStackTrace();
// Reading failed, try the next Reader
inputStream.seek(0);
}
finally {
reader.dispose();
}
}
}

当然,您可以组合使用以上选项,以兼顾两个方面的优势(即,如果一个阅读器出现故障,则订单稳定且回退)。





推荐阅读
  • 本文详细介绍了 `org.apache.tinkerpop.gremlin.structure.VertexProperty` 类中的 `key()` 方法,并提供了多个实际应用的代码示例。通过这些示例,读者可以更好地理解该方法在图数据库操作中的具体用途。 ... [详细]
  • Maven + Spring + MyBatis + MySQL 环境搭建与实例解析
    本文详细介绍如何使用MySQL数据库进行环境搭建,包括创建数据库表并插入示例数据。随后,逐步指导如何配置Maven项目,整合Spring框架与MyBatis,实现高效的数据访问。 ... [详细]
  • Beetl是一款先进的Java模板引擎,以其丰富的功能、直观的语法、卓越的性能和易于维护的特点著称。它不仅适用于高响应需求的大型网站,也适合功能复杂的CMS管理系统,提供了一种全新的模板开发体验。 ... [详细]
  • 本指南从零开始介绍Scala编程语言的基础知识,重点讲解了Scala解释器REPL(读取-求值-打印-循环)的使用方法。REPL是Scala开发中的重要工具,能够帮助初学者快速理解和实践Scala的基本语法和特性。通过详细的示例和练习,读者将能够熟练掌握Scala的基础概念和编程技巧。 ... [详细]
  • 本文详细介绍了如何使用C#实现不同类型的系统服务账户(如Windows服务、计划任务和IIS应用池)的密码重置方法。 ... [详细]
  • 本文详细探讨了Java中HashMap类的hash()方法的工作原理及其重要性,特别是在JDK 7版本中的实现。 ... [详细]
  • Spring Security基础配置详解
    本文详细介绍了Spring Security的基础配置方法,包括如何搭建Maven多模块工程以及具体的安全配置步骤,帮助开发者更好地理解和应用这一强大的安全框架。 ... [详细]
  • ASP.NET 进度条实现详解
    本文介绍了如何在ASP.NET中使用HTML和JavaScript创建一个动态更新的进度条,并通过Default.aspx页面进行展示。 ... [详细]
  • 在TypeScript中,我定义了一个名为 `Employee` 的接口,其中包含 `id` 和 `name` 属性。为了使这些属性可选为空,可以通过使用 `| null` 或 `| undefined` 来扩展其类型定义。例如,`id: number | null` 表示 `id` 可以是数字或空值。这种类型的灵活性在处理不确定的数据时非常有用,可以提高代码的健壮性和可维护性。 ... [详细]
  • 在过去,我曾使用过自建MySQL服务器中的MyISAM和InnoDB存储引擎(也曾尝试过Memory引擎)。今年初,我开始转向阿里云的关系型数据库服务,并深入研究了其高效的压缩存储引擎TokuDB。TokuDB在数据压缩和处理大规模数据集方面表现出色,显著提升了存储效率和查询性能。通过实际应用,我发现TokuDB不仅能够有效减少存储成本,还能显著提高数据处理速度,特别适用于高并发和大数据量的场景。 ... [详细]
  • 在第二课中,我们将深入探讨Scala的面向对象编程核心概念及其在Spark源码中的应用。首先,通过详细的实战案例,全面解析Scala中的类和对象。作为一门纯面向对象的语言,Scala的类设计和对象使用是理解其面向对象特性的关键。此外,我们还将介绍如何通过阅读Spark源码来进一步巩固对这些概念的理解。这不仅有助于提升编程技能,还能为后续的高级应用开发打下坚实的基础。 ... [详细]
  • 本文详细探讨了OpenCV中人脸检测算法的实现原理与代码结构。通过分析核心函数和关键步骤,揭示了OpenCV如何高效地进行人脸检测。文章不仅提供了代码示例,还深入解释了算法背后的数学模型和优化技巧,为开发者提供了全面的理解和实用的参考。 ... [详细]
  • Spring Batch 异常处理与任务限制优化策略 ... [详细]
  • 本文基于Java官方文档进行了适当修改,旨在介绍如何实现一个能够同时处理多个客户端请求的服务端程序。在前文中,我们探讨了单客户端访问的服务端实现,而本篇将深入讲解多客户端环境下的服务端设计与实现。 ... [详细]
  • 如何精通编程语言:全面指南与实用技巧
    如何精通编程语言:全面指南与实用技巧 ... [详细]
author-avatar
Idi-amin_643
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有