什么是可能的最小有效PDF?


139

出于好奇,看到最小的GIF,什么是最小的有效PDF文件?


取决于您如何创建它。很有可能您自己(在编辑器中)编写的代码比应用程序所生成的代码小。
devnull

尝试将“显示页面”(不带引号)输入到ghostscript或ps2pdf。
devnull

Answers:


194

这是一个有趣的问题。以书为准,您可以从以下内容开始:

%PDF-1.0
1 0 obj<</Type/Catalog/Pages 2 0 R>>endobj 2 0 obj<</Type/Pages/Kids[3 0 R]/Count 1>>endobj 3 0 obj<</Type/Page/MediaBox[0 0 3 3]>>endobj
xref
0 4
0000000000 65535 f
0000000010 00000 n
0000000053 00000 n
0000000102 00000 n
trailer<</Size 4/Root 1 0 R>>
startxref
149
%EOF

PDF喜悦的291个字节。Acrobat将其打开,但是有些抱怨。其中有一页,它是3/72“平方,这是规范允许的最小值。

但是,Acrobat X甚至不再理会交叉引用表,因此我们可以将其删除:

%PDF-1.0
1 0 obj<</Type/Catalog/Pages 2 0 R>>endobj 2 0 obj<</Type/Pages/Kids[3 0 R]/Count 1>>endobj 3 0 obj<</Type/Page/MediaBox[0 0 3 3]>>endobj
trailer<</Size 4/Root 1 0 R>>

Acrobat抱怨了,但打开了它。现在我们有178个字节。事实证明,您在预告片中不需要该/ Size。现在我们在172:

%PDF-1.0
1 0 obj<</Type/Catalog/Pages 2 0 R>>endobj 2 0 obj<</Type/Pages/Kids[3 0 R]/Count 1>>endobj 3 0 obj<</Type/Page/MediaBox[0 0 3 3]>>endobj
trailer<</Root 1 0 R>>

原来,您不需要字典中所有讨厌的/ Type元素:

%PDF-1.0
1 0 obj<</Pages 2 0 R>>endobj 2 0 obj<</Kids[3 0 R]/Count 1>>endobj 3 0 obj<</MediaBox[0 0 3 3]>>endobj
trailer<</Root 1 0 R>>

现在我们有138个字节。

事实证明,当规范说“必须是间接引用”并且需要/ Count并且标头“必须”为%PDF-1.0时,他们在提出宽松的建议。这是我能做的最小的,并且可以在Acrobat X中打开:

%PDF-1.
trailer<</Root<</Pages<</Kids[<</MediaBox[0 0 3 3]>>]>>>>>>

70个字节

现在,我的编辑器使用Windows换行规则,但是Acrobat接受Windows,Mac或Unix约定,因此通过使用十六进制编辑器,我用\ r替换了\ r \ n并删除了最后一个换行符,这使我剩下67个字节

25 50 44 46 2D 31 2E 0D 74 72 61 69 6C 65 72 3C 
3C 2F 52 6F 6F 74 3C 3C 2F 50 61 67 65 73 3C 3C 
2F 4B 69 64 73 5B 3C 3C 2F 4D 65 64 69 61 42 6F 
78 5B 30 20 30 20 33 20 33 5D 3E 3E 5D 3E 3E 3E 
3E 3E 3E 

我尝试摘下最后一个词典(>>),但Acrobat则没有。内置于Google Chrome浏览器(FoxIt)的PDF阅读无法打开。

作为PostScript(HA!看看我在那儿做了什么?),如果您同意Acrobat“修复”文件,它将增加3550字节,其中大多数是可选的元数据,但它留下了许多明显的违反规范的地方。


25
事实证明,当规范说“必须是间接引用”并且需要/ Count并且标头“必须”为%PDF-1.0时,他们在提出宽松的建议。不,这些不是宽松的建议,这些是有效性的要求。即使某些PD​​F查看器不强制执行,但不遵循它们也意味着无效,OP要求提供有效的PDF。
mkl

23
接受,因为答案以开头minimum allowed by the spec,然后超出其他范围。好答案,谢谢!:)
Meshy 2013年

plith,这是一个了不起的答案。现在,如何在其中包含一行文本的最小有效pdf,例如“ Hello World”。我以为它就像添加{stream BT(“ Hello World”)ET endstream}一样简单,但到目前为止还无法使Acrobat满意。
neonzeon

1
那是规格。PDF中的对象图具有循环。
2013年

1
@towi您的base64编码版本已\n嵌入其中,当base64解码后无法提供正确的文件内容。
Christopher Schultz

19

我无法打开您好的世界示例。

对于带有文本内容的小文件:

%PDF-1.2 
9 0 obj
<<
>>
stream
BT/ 9 Tf(Test)' ET
endstream
endobj
4 0 obj
<<
/Type /Page
/Parent 5 0 R
/Contents 9 0 R
>>
endobj
5 0 obj
<<
/Kids [4 0 R ]
/Count 1
/Type /Pages
/MediaBox [ 0 0 99 9 ]
>>
endobj
3 0 obj
<<
/Pages 5 0 R
/Type /Catalog
>>
endobj
trailer
<<
/Root 3 0 R
>>
%%EOF

2
这将不起作用,您需要定义字体资源,然后在页面内容中选择它,以显示文本。
yms 2015年

2
该文件实际上是在Mac OS X El Capitan下打开的,而PDF1.0中评分最高的答案却没有。
Devy

12
此外,根据铬,数据打开:应用/ PDF; BASE64,JVBERi0xLjIgCjkgMCBvYmoKPDwKPj4Kc3RyZWFtCkJULyA5IFRmKFRlc3QpJyBFVAplbmRzdHJlYW0KZW5kb2JqCjQgMCBvYmoKPDwKL1R5cGUgL1BhZ2UKL1BhcmVudCA1IDAgUgovQ29udGVudHMgOSAwIFIKPj4KZW5kb2JqCjUgMCBvYmoKPDwKL0tpZHMgWzQgMCBSIF0KL0NvdW50IDEKL1R5cGUgL1BhZ2VzCi9NZWRpYUJveCBbIDAgMCA5OSA5IF0KPj4KZW5kb2JqCjMgMCBvYmoKPDwKL1BhZ2VzIDUgMCBSCi9UeXBlIC9DYXRhbG9nCj4 + CmVuZG9iagp0cmFpbGVyCjw8Ci9Sb290IDMgMCBSCj4 + CiUlRU9G
卢克Rehmann

8

我以为我会制作一个最小的pdf文件,显示“ Hello World”。文本在左下角。很抱歉9点字体,任何较大的字体都会花费一个额外的字节:)

Adobe Reader X的172个字节(如果与仅换行符一起保存,并且没有尾随换行符或空字节):

%PDF-1.
1 0 obj<</Kids[<</Parent 1 0 R/Resources<<>>/Contents 2 0 R>>]>>endobj 2 0 obj<<>>stream
BT/ 9 Tf(Hello World)' ET
endstream
endobj trailer<</Root<</Pages 1 0 R>>>>

Chrome的内置PDF查看器的120个字节:

%PDF 1 0 obj<</Pages<</Kids[<</Contents<<>>stream
BT 9 Tf(Hello World)' ET endstream>>]>>>>endobj trailer<</Root 1 0 R>>

要在Chrome中轻松查看此内容,请将此URI粘贴到地址栏中(因此,我不允许我链接到它,并且在其他浏览器中也无法使用):

data:application/pdf,%25PDF%201%200%20obj%3C%3C%2FPages%3C%3C%2FKids%5B%3C%3C%2FContents%3C%3C%3E%3Estream%0ABT%209%20Tf(Hello%20World)'%20ET%20endstream%3E%3E%5D%3E%3E%3E%3Eendobj%20trailer%3C%3C%2FRoot%201%200%20R%3E%3E

2
很小 ;)根据规范无效。
mkl 2014年

8
不会在Chrome中为我打开。
路加·雷曼

0

在Java中,使用以下命令:

 private static String samplepdf = "255044462D312E0D747261696C65723C3C2F526F6F743C3C2F50616765733C3C2F4B6964735B3C3C2F4D65646961426F785B302030203320335D3E3E5D3E3E3E3E3E3E";

然后

byte[] bytes = hexStringToByteArray(samplepdf);

...

public byte[] hexStringToByteArray(String s) {
    int len = s.length();
    byte[] data = new byte[len / 2];
    for (int i = 0; i < len; i += 2) {
        data[i / 2] = (byte) ((Character.digit(s.charAt(i), 16) << 4)
                + Character.digit(s.charAt(i + 1), 16));
    }
    return data;
}

OP要求最小的有效PDF文件 ; 根据规范,您的是无效的。
mkl
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.