flatten a struct of arbitrarily nested arrays of integers into a flat array of integers

前端 未结 2 1617
余生分开走
余生分开走 2021-01-20 04:22

Is it possible to flatten an array of arbitrarily nested arrays of integers into a flat array of integers in Matlab? For example,

[[1,2,[3]],4] -> [1,2,3         


        
相关标签:
2条回答
  • 2021-01-20 04:32

    I think you will have to adapt the flatten function from the file exchange to use struct2cell so something like this:

    function C = flatten_struct(A)
    
        A = struct2cell(A);
        C = [];
        for i=1:numel(A)  
            if(isstruct(A{i}))
                C = [C,flatten_struct(A{i})];
            else
                C = [C,A{i}]; 
            end
        end
    
    end
    

    This results in:

    a.c = [5,4];
    a.b.a=[9];
    a.b.d=[1,2];
    
    flatten_struct(a)
    
    ans =
    
        5    4    9    1    2
    

    So the order is in the order you declared your struct instead of in your example order which I presume is alphabetical. But you have control over this so it shouldn't be a problem.

    0 讨论(0)
  • 2021-01-20 04:47

    I have a preliminary hack which does work but rather clumsily. It descends recursively, saving structure names and unpacking the returned structure at each "level" .

    %  struct2sims converter
    function simout = struct2sims(structin)
    fnam = fieldnames(structin);
    for jf = 1:numel(fnam)
        subnam = [inputname(1),'_',fnam{jf}];
        if isstruct(structin.(fnam{jf}) ) ,
        % need to dive;  build a new variable that's not a substruct
         eval(sprintf('%s = structin.(fnam{jf});', fnam{jf}));
        eval(sprintf('simtmp = struct2sims(%s);',fnam{jf}) );
        % try removing the struct before getting any farther...
        simout.(subnam) = simtmp;
        else
        % at bottom, ok
        simout.(subnam) = structin.(fnam{jf});
        end
    
    end
     %  need to unpack structs here, after each level of recursion
     % returns...
        subfnam = fieldnames(simout);
        for kf = 1:numel(subfnam)
             if isstruct(simout.(subfnam{kf}) ),  
                 subsubnam = fieldnames(simout.(subfnam{kf}));
                 for fk = 1:numel(subsubnam)
                     simout.([inputname(1),'_',subsubnam{fk}])...
                         = simout.(subfnam{kf}).(subsubnam{fk}) ;
                 end
                 simout = rmfield(simout,subfnam{kf});
             end
        end
     % if desired write to file with:
     % save('flattened','-struct','simout');
    end
    
    0 讨论(0)
提交回复
热议问题