"Depende do sistema de arquivos"
Alguns usuários mencionaram que o impacto no desempenho depende do sistema de arquivos usado. Claro. Sistemas de arquivos como o EXT3 podem ser muito lentos. Mas mesmo se você usar EXT4 ou XFS você não pode impedir que o listando uma pasta através de ls
ou find
ou através de uma conexão externa como FTP vai se tornar mais lenta uma mais lenta.
Solução
Prefiro da mesma maneira que @armandino . Para isso, uso essa pequena função no PHP para converter IDs em um caminho de arquivo que resulta em 1000 arquivos por diretório:
function dynamic_path($int) {
// 1000 = 1000 files per dir
// 10000 = 10000 files per dir
// 2 = 100 dirs per dir
// 3 = 1000 dirs per dir
return implode('/', str_split(intval($int / 1000), 2)) . '/';
}
ou você pode usar a segunda versão se desejar usar caracteres alfanuméricos:
function dynamic_path2($str) {
// 26 alpha + 10 num + 3 special chars (._-) = 39 combinations
// -1 = 39^2 = 1521 files per dir
// -2 = 39^3 = 59319 files per dir (if every combination exists)
$left = substr($str, 0, -1);
return implode('/', str_split($left ? $left : $str[0], 2)) . '/';
}
resultados:
<?php
$files = explode(',', '1.jpg,12.jpg,123.jpg,999.jpg,1000.jpg,1234.jpg,1999.jpg,2000.jpg,12345.jpg,123456.jpg,1234567.jpg,12345678.jpg,123456789.jpg');
foreach ($files as $file) {
echo dynamic_path(basename($file, '.jpg')) . $file . PHP_EOL;
}
?>
1/1.jpg
1/12.jpg
1/123.jpg
1/999.jpg
1/1000.jpg
2/1234.jpg
2/1999.jpg
2/2000.jpg
13/12345.jpg
12/4/123456.jpg
12/35/1234567.jpg
12/34/6/12345678.jpg
12/34/57/123456789.jpg
<?php
$files = array_merge($files, explode(',', 'a.jpg,b.jpg,ab.jpg,abc.jpg,ddd.jpg,af_ff.jpg,abcd.jpg,akkk.jpg,bf.ff.jpg,abc-de.jpg,abcdef.jpg,abcdefg.jpg,abcdefgh.jpg,abcdefghi.jpg'));
foreach ($files as $file) {
echo dynamic_path2(basename($file, '.jpg')) . $file . PHP_EOL;
}
?>
1/1.jpg
1/12.jpg
12/123.jpg
99/999.jpg
10/0/1000.jpg
12/3/1234.jpg
19/9/1999.jpg
20/0/2000.jpg
12/34/12345.jpg
12/34/5/123456.jpg
12/34/56/1234567.jpg
12/34/56/7/12345678.jpg
12/34/56/78/123456789.jpg
a/a.jpg
b/b.jpg
a/ab.jpg
ab/abc.jpg
dd/ddd.jpg
af/_f/af_ff.jpg
ab/c/abcd.jpg
ak/k/akkk.jpg
bf/.f/bf.ff.jpg
ab/c-/d/abc-de.jpg
ab/cd/e/abcdef.jpg
ab/cd/ef/abcdefg.jpg
ab/cd/ef/g/abcdefgh.jpg
ab/cd/ef/gh/abcdefghi.jpg
Como você pode ver na $int
versão -, cada pasta contém até 1000 arquivos e até 99 diretórios, contendo 1000 arquivos e 99 diretórios ...
Mas não esqueça que muitos diretórios causam os mesmos problemas de desempenho!
Finalmente, você deve pensar em como reduzir a quantidade de arquivos no total. Dependendo do seu objetivo, você pode usar sprites CSS para combinar várias imagens minúsculas, como avatares, ícones, smilies, etc. No meu caso, eu tinha milhares de mini-caches e finalmente decidi combiná-los em pacotes de 10.