2012-08-12 68 views
0

我正在实现的一个API处理包含分层结构化数据的InputStreams,即嵌套块(包括叶块中的多个图像)。 (如果您必须知道,我解析的数据是CBEFF。)每个数据块都以包含有关该块的一些元数据的标题为前缀。通过提供InputStream getter来延迟访问InputStream

1st level 1 header 
    1st level 2 header 
    1st level 2 data block 
    2nd level 2 header 
    2nd level 2 data block 
2nd level 1 header 
    3rd level 2 header 
    3rd level 2 data block 

原始的InputStream是我的API类的构造函数的参数,并沿层次传递。 目前我正在将图像读入我的API类构造函数中的字节数组中,因此每个构造函数都会在读取该类负责的完整数据时阻塞,并且稍后客户端调用该API类的相关getter方法时,它们将获取从内存中提供的图像数据。我更愿意以某种惰性InputStream的形式向我的API的客户端提供所包含的图像,以便图像字节仅从原始InputStream中读取,因为客户端读取由吸气。这使得例如可以进行渐进式渲染,这在原始InputStream较慢时很有用。

有没有一种优雅的方式来解决这与InputStreams?

+0

错误,只是删除所有的图像阅读代码? – EJP 2012-08-13 01:02:42

+0

@EJP,是的,如果只有一个图像,并且图像数据是InputStream中的最后一个元素,它就可以工作。我有多个图像,图像_n_ + 1的标题跟在图像_n_的数据之后。我会澄清这个问题。 – martijno 2012-08-13 07:07:47

回答

1

InputStream不适合随机存取。因此,在大多数情况下,读取部分文件并不会起作用,即使您可以使用resetskip的组合在某些输入流上实现类似效果。但并不是所有的流支持reset,并且跳过字节通常与读取字节一样昂贵。

所以我建议你尝试一些替代方法。您可以将整个流缓冲到某个随机访问缓冲区,如临时文件,这意味着首先从流中读取所有字节。或者您可以找到一种方法来随机访问原始来源。您没有指定要处理的来源的类型,但例如对于HTTP连接,您可以使用range requestdownload parts。类似的解决方案可能适用于其他来源

不管你如何实现随机存取(和看到你的评论,你可能会这样做使用带有resetskipInputStream),你可以创建自己的类来表示流的一部分。通过继承FilterInputStream,您可以让该类本身成为InputStream的实例。

cLass SubStream extends FilterInputStream { 
    private long offset; 
    public SubStream(long offset, InputStream parent) { 
     super(parent); 
     this.offset = offset; 
    } 
    public SubStream(InputStream parent) { 
     this(0, parent); 
    } 
    @Override public void reset() throws IOException { 
     in.reset(); 
     in.skip(offset); 
    } 
    public SubStream subStream(long offset) { 
     return new FilterInputStream(this.offset + offset, in); 
    } 
    public Object syncObject() { 
     return in; 
    } 
} 

你必须确保使用这些流之一任何操作调用reset第一。如果您需要强制执行正确的流结束处理,则必须覆盖大多数read实现。如果可能有并发访问,那么您将需要同步基础流上的操作。所以使用这个类的代码可能看起来像这样:

 synchronized(part.syncObject()) { 
     part.reset(); 
     return read(part); 
    } 
+0

来源是智能卡读卡器中的智能卡(所以,连接速度非常慢,我们在这里只说几kbps,因此需要支持渐进式渲染)。支持标记和重置,并且跳过很便宜。 – martijno 2012-08-13 10:12:32