Philippe Fisher
Philippe Fisher

Reputation: 596

Python recursively appending list function

Having issues with a recursive function that should be relatively simple to do, but can`t seem to get right.

I have a folder structure with folders that can contain other folders, images or files. Associated with each folder there are permissions. I want to have my function recursively build a list of the permissions that are associated with each folder.

I have a function has_read_permission(request) that returns True if the folder has permissions and False if not

I have built a function like so:

def get_child_perms(self, folder, request, perm_list):
        # Folder contains other folders
        if folder.get_children():
            # For every sub-folder
            for subfolder in folder.get_children():
                return perm_list.append(self.get_child_perms(subfolder, request, perm_list))
        else:
            # If folder doesn't have sub-folders containing folders
            return [folder.has_read_permission(request)]

I keep getting None

Given folders like so:

Folder (allowed) - Wont check this one
|_First Folder (allowed)
| |_First sub Folder (restricted)
| | |_File
| | |_File
| | |_Image
| |__Second Sub Folder (allowed)
|_Second Folder (allowed)

Then running get_child_perms() would return [True,False,True,True] or even [True, [False, True], True]

EDIT

Disregard edit -> asked other question Python Recursive function missing results

Changed abit,

def get_child_perms(self, folder, request, perm_list):
        if folder.get_children():
            for subfolder in folder.get_children():
                perm_list.append(self.get_child_perms(subfolder, request, perm_list))
            return perm_list
        else:
            return [folder.has_read_permission(request)]

getting:

[[True], [...], [True], [...], [...], [True], [True], [True], [True], [True], [True], [True], [True], [...], [True], [...]]

 Admin
 -Folder 1
   - Files
 -Folder 2
   - Files
 -Folder 3
   - Files 
 -Folder 4
   - SubFolder 1
      -SubSubFolder 1
         - Files
      - Files
   - SubFolder 2
      - SubSubFolder 2
           - Files
      - Files
 -Folder 5
   - SubFolder 3
       - Files
   - SubFolder 4
       - Files
   - SubFolder 5
       -Files
   - Files
 -Folder 6
   - Files
 -Folder 7
   - SubFoler 6
       - Files
   - Files
 -Folder 8
   - Files

Upvotes: 1

Views: 770

Answers (3)

vks
vks

Reputation: 67968

for subfolder in folder.get_children():
    perm_list.append(self.get_child_perms(subfolder, request, perm_list))
return perm_list

.append is in place. It does not return anything.So you are getting None

Upvotes: 4

Padraic Cunningham
Padraic Cunningham

Reputation: 180391

As pointed out append is an inplace operation that returns None, you can avoid using append at all by returning a list comp:

def get_child_perms(self, folder, request, perm_list):
    # Folder contains other folders
    children =  folder.get_children()
    if children:
        # For every sub-folder
        return [self.get_child_perms(subfolder, request, perm_list)
                for subfolder in children]
    return [folder.has_read_permission(request)]

You don't need an else either as you can only return once from the function.

Upvotes: 1

Two-Bit Alchemist
Two-Bit Alchemist

Reputation: 18457

In-place list methods return None to remind you that they operate in place.

Instead of:

return permlist.append(self.get_child_perms(...  # etc.

Try:

permlist.append(self.get_child_perms(...
return permlist

Edited to add: As other comments/answers have pointed out, you'll want to return outside your for loop if you want it to complete.

Upvotes: 3

Related Questions