递归列出文件名,dir的CSV

时间:2017-11-22 05:07:07

标签: bash shell loops csv recursion

假装我的根是: repeats

我的文件夹结构为:

foo

目录可能更深一些文件夹。

如果我有这样的根:

-foo -123 -file.jpg -file2.jpg -456 -file.jpg -file2.jpg

我如何在shell脚本中以CSV格式列出每个文件名及其路径?

我尝试了一些答案,但我很难让它输出一长串CSV。

我期待的是:

ROOT=foo

所以,我试过这个:

file.jpg,123,file2.jpg,123,file.jpg,456,file2.jpg,456

它不断为我的输出添加句点,我不相信我的递归部分也是正确的。有人可以指出我正确的方向或可能有帮助的文件吗?

我在shell脚本方面做得很少,但我正在尝试:)基本上要接受这个答案并导出到整个目录的CSV并提供带有dir路径的图像链接(相对于初始目录),便于过滤导入Excel。

2 个答案:

答案 0 :(得分:1)

如果你有bash

,这可以轻松完成,而不是GNU find
find foo -type f -printf '"%f","%h"\n' | paste -d, -s -
  • %f for filename
  • %h用于主要目录路径
  • paste -d, -s -将换行符分隔的结果连接到逗号分隔的单行

BSD find更通用的解决方案,因为它不支持-printf选项

find foo -type f -print | sed 's|^\(.*\)/\(.*\)|"\2","\1"|' | paste -d, -s -

<强>输出

"file1.jpg","foo/123","file2.jpg","foo/123","file1.jpg","foo/456","file2.jpg","foo/456"

要生成快速测试用例,您可以使用

mkdir -p foo/{123,456}
touch foo/{123,456}/file{1..2}.jpg

生成类似

的目录结构
foo/
├── 123
│   ├── file1.jpg
│   └── file2.jpg
└── 456
    ├── file1.jpg
    └── file2.jpg

答案 1 :(得分:0)

既然你想要:

  • 无领导期
  • 处理文件夹
  • 单行CSV

你可以有两个约定(基于我对你的例子的理解):

  1. 列出如:
    t = int(input())
    for i in range (t):
        n = int(input())
        if (n >= 1000000007):
            fact_n = 0
        else:
            fact_n = 1
            for i in range(1,n+1):
                fact_n = (fact_n * i) % 1000000007
        print(fact_n)
    
  2. 列出如:
    full/folder/file  ,  full/folder/file
  3. 假设我当前的目录 foo 如下所示:

    full/folder  ,  file  ,  full/folder  ,  file

    然后是第一个约定:

    14:37:14 ツ :foo >ls -R
    sublevel1        456            123
    
    ./sublevel1:
    123
    
    ./sublevel1/123:
    file2.jpg file.jpg
    
    ./456:
    file2.jpg file.jpg
    
    ./123:
    file2.jpg file.jpg
    

    这会给你以下结果:

    #!/usr/bin/env bash
    first=1
    find . -type f -print0 | while IFS= read -rd '' file ; do 
        if [ "$first" == "1" ]; then 
            filestr="\"$(cut -f2- -d'/' <<< "${file}")\""
            unset first
       else 
            filestr=",\"$(cut -f2- -d'/' <<< "${file}")\""  
            fi
       printf "%s" "$filestr"
    done
    

    如果您将"sublevel1/123/file.jpg","sublevel1/123/file2.jpg","456/file.jpg","456/file2.jpg","123/file.jpg","123/file2.jpg" 更改为-print0,那么您将获得类似上述第二个约定的输出:

    -printf "%h\0%f\0"

    注意:

    • null (\ 0,-print0)处理使得处理奇怪的文件名更加可靠,甚至可能是带有嵌入换行符的文件名。
    • 当字符串正确传递给程序时,"sublevel1/123","file.jpg","sublevel1/123","file2.jpg","456","file.jpg","456","file2.jpg","123","file.jpg","123","file2.jpg" 格式在处理名称方面具有相当的弹性
    • printf "%s"块只是为了确保逗号不以第一个文件为前缀
    • 对于想要单个字符串csv列表的任何可能的使用,“while”循环的低效率不应该是显而易见的。
    • 我添加了 sublevel1 来演示多个文件夹级别。

    对于更强大的应用程序,请考虑序列化JSON或其他一些数据表示格式,其中可以更完整地处理列表处理。