Rumah  >  Artikel  >  pembangunan bahagian belakang  >  Kosongkan folder daripada pepohon yang mengandungi hanya folder kosong

Kosongkan folder daripada pepohon yang mengandungi hanya folder kosong

WBOY
WBOYke hadapan
2024-02-09 09:54:101162semak imbas

Kosongkan folder daripada pepohon yang mengandungi hanya folder kosong

Editor php Xiaoxin di sini untuk memperkenalkan anda kepada sedikit helah tentang operasi folder - cara mengosongkan folder yang hanya mengandungi folder kosong daripada pokok. Dalam pengurusan fail harian, kami mungkin menemui beberapa folder yang hanya mengandungi folder kosong Folder ini menduduki ruang storan tetapi tidak mempunyai kandungan sebenar. Melalui operasi mudah berikut, kami boleh mengosongkan folder kosong ini dengan mudah, mengosongkan ruang storan berharga dan meningkatkan kecekapan pengurusan fail.

Kandungan soalan

Saya ada satu

type node struct {
   id       string
   children []node
}

Saya mempunyai struktur direktori yang dimodelkan selepas kepingan ini. Mungkin terdapat pelbagai peringkat struktur folder dalam direktori ini, berakhir tanpa fail di dalamnya. Lihat: ű

folder1/folder2/folder3/folder4
folder1/file1.txt

Saya mahu membersihkan folder yang hanya mempunyai folder kosong. Jadi, dalam contoh ini, hanya satu fail akan kekal dalam folder1 dan semua di bawah akan dipadamkan. Tetapi saya nampaknya tidak dapat menghasilkan idea yang baik untuk melakukan ini. Saya pasti boleh mencipta pokok baharu tanpa menukar pokok asal, tetapi saya tidak tahu cara untuk melelakan dengan cekap melalui pokok itu dan melihat jika anak terakhir tidak mempunyai anak, kemudian kembali ke akar dan padamkan kanak-kanak itu yang mengakibatkan hanya senarai folder kosong. Sebarang idea akan dialu-alukan!

Penyelesaian awal saya untuk hanya memadamkan daun dan bukan folder induk:

func removeChildlessFolders(original, tree []Node) []Node {
    for i, node := range original {
        if len(node.Children) == 0 {
            continue
        }

        dir := Node{}
        dir.Id = node.Id
        dir.Children = append(dir.Children, node.Children...)
        tree = append(tree, dir)
        removeChildlessFolders(original[i].Children, node.Children)
    }

    return tree
}

Penyelesaian

Soalan yang bagus dahulu, tetapi sukar bagi orang lain untuk menghasilkan semula kes penggunaan yang anda miliki. Dari kali seterusnya cuba tambah kod yang boleh dihasilkan semula yang boleh digunakan oleh orang ramai dan cepat menguji kaedah mereka dan memberikan hasil. Seperti anda telah melepasi akar tetapi bagaimana anda memulakannya? Jika seseorang perlu membantu anda, mereka perlu membina hubungan terlebih dahulu. Secara umumnya, ini menyusahkan. Walau bagaimanapun, mari kita lihat penyelesaiannya.

Struktur direktori

输入dir

test-folder
├── folder1
│   └── folder2
│       └── folder3
├── folder4
│   ├── folder5
│   └── joker
└── folder6
    └── file.txt

预期结果

test-folder
└── folder6
    └── file.txt

Takrifan nod

Pertama sekali, saya tidak tahu bagaimana anda mencipta pepohon direktori. Jika anda mengekodkannya, itu adalah soalan yang berbeza, tetapi n-ary 树通常填充的方式,那么您需要使用自引用指针定义 node . Bukan kepingan yang tepat. Jadi saya akan mentakrifkan nod seperti berikut

type node struct {
    id       string
    children []*node
}

Kaedah pembantu

Ini ialah kaedah pembantu untuk menyemak sama ada laluan menghala ke direktori

func ifdir(path string) bool {
    file, err := os.open(path)
    if err != nil {
        panic(err)
    }
    defer file.close()
    info, err := file.stat()
    if err != nil {
        panic(err)
    }
    if info.isdir() {
        return true
    }
    return false
}

Cara mengisi pokok

Ini menggunakan queue 输入 n-ary 树 的简单迭代方法。 golang不提供队列实现,但golang通道实际上只是队列。我将其保留为 500 kerana kami tidak boleh mencipta saluran penimbal dinamik dalam golang. IMHO, nombor ini sepatutnya berfungsi untuk hampir semua senario.

func buildtreefromdir(basedir string) *node {
    _, err := ioutil.readdir(basedir)
    if err != nil {
        return nil
    }
    root := &node{
        id: basedir,
    }
    //////////
    queue := make(chan *node, 500) // consider that there can not be any dir with > 500 depth
    queue <- root
    for {
        if len(queue) == 0 {
            break
        }
        data, ok := <-queue
        if ok {
            // iterate all the contents in the dir
            curdir := (*data).id
            if ifdir(curdir) {
                contents, _ := ioutil.readdir(curdir)

                data.children = make([]*node, len(contents))
                for i, content := range contents {
                    node := new(node)
                    node.id = filepath.join(curdir, content.name())
                    data.children[i] = node
                    if content.isdir() {
                        queue <- node
                    }
                }
            }
        }
    }
    return root
}

Kaedah tambahan lain

Ini hanya mencetak pepohon direktori. Untuk tujuan penyahpepijatan sahaja.

func printdirtree(root *node) {
    fmt.println(root.id)
    for _, each := range root.children {
        printdirtree(each)
    }
    if len(root.children) == 0 {
        fmt.println("===")
    }

}

Akhirnya penyelesaian anda.

Sangat mudah. Jika anda mempunyai sebarang pertanyaan sila beritahu saya.

func recursiveemptydelete(root *node) {
    // if the current root is not pointing to any dir
    if root == nil {
        return
    }
    for _, each := range root.children {
        recursiveemptydelete(each)
    }
    if !ifdir(root.id) {
        return
    } else if content, _ := ioutil.readdir(root.id); len(content) != 0 {
        return
    }
    os.remove(root.id)
}

Ini adalah main()

func main() {
    root := buildTreeFromDir("test-folder")
    printDirTree(root)
    recursiveEmptyDelete(root)
}

Atas ialah kandungan terperinci Kosongkan folder daripada pepohon yang mengandungi hanya folder kosong. Untuk maklumat lanjut, sila ikut artikel berkaitan lain di laman web China PHP!

Kenyataan:
Artikel ini dikembalikan pada:stackoverflow.com. Jika ada pelanggaran, sila hubungi admin@php.cn Padam