1. fetch & store

Here is a proposal for the replacement of fetch and store.

  • get_object returns a default value when object is not found in sequence instead of providing an error message.
  • set_object simply doesn't the job if the path to storage location cannot be followed to its end instead of providing an error message.
include std/search.e 
include std/types.e 
 
------------------------------------------------------------------------------ 
 
function get_object(object structure, sequence target, object default=0, sequence path={}) 
  if atom(structure) then 
    if equal(path, target) then return structure end if 
  else 
    if t_text(structure) then 
      if equal(path, target) then return structure end if 
    else   
      for i=1 to length(structure) do 
        if sequence(structure[i]) then 
          object o = get_object(structure[i], target, default, path&i) 
          if not equal(o, default) then 
            return o   
          end if 
        else 
          if equal(path, target) then return structure end if 
        end if 
      end for 
    end if 
  end if 
  return default 
end function 
 
------------------------------------------------------------------------------ 
 
function set_object(object structure, sequence target, object x, sequence path={}) 
  if atom(structure) then 
    if equal(path, target) then structure = x end if 
  else 
    if t_text(structure) then 
      if equal(path, target) then structure = x end if 
    else   
      for i=1 to length(structure) do 
        if sequence(structure[i]) then 
          if begins(path, target) then 
            structure[i] = set_object(structure[i], target, x, path&i) 
          end if 
        else 
          if equal(path, target) then structure[i] = x end if 
        end if 
      end for 
    end if 
  end if 
  return structure 
end function 

Here is an example of usage:

include std/pretty.e 
include std/console.e 
 
sequence structure = {{{"admin", {"software"}}}, {{"configure", {"access-control"}}}} 
 
pretty_print(1, structure, {3}) 
puts(1, "\n") 
printf(1, "get_object(structure, {1,1,2,1}) = %s\n", {get_object(structure, {1,1,2,1})}) 
structure = set_object(structure, {1,1,2,1}, "new") 
pretty_print(1, structure, {3}) 
puts(1, "\n") 
printf(1, "get_object(structure, {1,1,2,1}) = %s\n", {get_object(structure, {1,1,2,1})}) 
structure = set_object(structure, {1,3}, "added")  -- path not found, no crash 
pretty_print(1, structure, {3}) 
puts(1, "\n") 
maybe_any_key() 

Jean-Marc

new topic     » topic index » view message » categorize

2. Re: fetch & store

Here is an update: now set_object can add items in a nested sequence even if there is no path to that location, what store cannot do.

include std/search.e 
include std/types.e 
include std/text.e 
 
public function get_object(object structure, sequence target, object default=0, sequence path={})  
  if atom(structure) then  
    if equal(path, target) then 
      return structure 
    end if  
  else  
    if t_text(structure) then  
      if equal(path, target) then 
        return structure 
      end if  
    else    
      integer digit = target[length(path)+1] 
      for i = 1 to digit do 
        if sequence(structure[i]) then  
          if i = digit then  
            object o = get_object(structure[i], target, default, path&i)  
            if not equal(o, default) then return o end if  
          end if  
        else  
          if equal(path, target) then 
            return structure 
          end if  
        end if  
      end for  
    end if  
  end if  
  return default  
end function  
  
------------------------------------------------------------------------------  
  
public function set_object(object structure, sequence target, object x, sequence path={})  
  integer level = length(path)+1 
  if atom(structure) then  
    if equal(path, target) then 
      structure = x 
    end if  
  else  
    integer lg = length(structure)   
    if lg and t_text(structure) then  
      if equal(path, target) then 
        structure = x 
      else 
        structure[target[level]] = set_object(structure[target[level]], target, x, path&target[level]) 
      end if  
    else 
      integer digit = target[level] 
      for i = 1 to digit do 
        if i <= lg then  
          if i = digit then  
            if sequence(structure[i]) then  
              structure[i] = set_object(structure[i], target, x, path&i) 
            else 
              structure[i] = x 
            end if  
          end if 
        else 
          structure = append(structure, {}) 
          if i = digit then  
            if level < length(target) then  
              structure[i] = set_object(structure[i], target, x, path&i) 
            else 
              structure[i] = x 
            end if  
          end if 
        end if  
      end for  
    end if  
  end if  
  return structure  
end function 

Example:

include std/pretty.e  
include std/console.e  
  
sequence structure = {{{"admin", {"software"}}}, {{"configure", {"access-control"}}}}  
  
pretty_print(1, structure, {3})  
puts(1, "\n")  
 
-- conventional part 
 
printf(1, "get_object(structure, {1,1,2,1}) = %s\n", {get_object(structure, {1,1,2,1})})  
 
structure = set_object(structure, {1,1,2,1}, "modified") 
pretty_print(1, structure, {3})  
puts(1, "\n")  
 
-- and now the magic part: adds new items out of current locations 
 
structure = set_object(structure, {1,3}, "added")  
pretty_print(1, structure, {3})  
puts(1, "\n")  
 
structure = set_object(structure, {1,2,1}, "added") 
pretty_print(1, structure, {3})  
puts(1, "\n")  
 
structure = set_object(structure, {1,2,1,1}, 'A') 
pretty_print(1, structure, {3})  
puts(1, "\n")  
 
structure = set_object(structure, {4,1}, "added") 
pretty_print(1, structure, {3})  
puts(1, "\n")  
 
maybe_any_key() 

For Eu3.11 use is_string from Eu3 Standard Library instead of t_text.

For Phix, use string instead f t_text.

Jean-Marc

new topic     » goto parent     » topic index » view message » categorize

3. Re: fetch & store

I have drastically reduced the size of my recursive functions for nested sequence management and I added a removal function.

include std/search.e 
include std/text.e 
 
-------------------------------------------------------------------------------- 
  
public function get_nested(object structure, sequence targetPath, object def=0, 
                           sequence currentPath={})  
  if equal(currentPath, targetPath) then 
    return structure 
  else 
    integer digit = targetPath[length(currentPath)+1] 
    if digit <= length(structure) then 
      return get_nested(structure[digit], targetPath, def, currentPath&digit) 
    else 
      return def 
    end if 
  end if 
end function  
  
-------------------------------------------------------------------------------- 
  
public function set_nested(object structure, sequence targetPath, 
                           object x, sequence currentPath={})  
  integer digit = targetPath[length(currentPath)+1] 
  for i = 1 to digit do 
    if i > length(structure) then 
      structure = append(structure, {}) 
    end if 
    if i = digit then  
      if equal(currentPath&{i}, targetPath) then 
        structure[i] = x 
      else 
        structure[i] = set_nested(structure[i], targetPath, x, currentPath&i) 
      end if 
    end if 
  end for 
  return structure  
end function 
 
-------------------------------------------------------------------------------- 
 
public function remove_nested(object structure, sequence targetPath, 
                              sequence currentPath={}) 
  integer digit = targetPath[length(currentPath)+1] 
  if digit <= length(structure) then 
    if equal(currentPath&{digit}, targetPath) then 
      structure = remove(structure, digit) 
    else 
      structure[digit] = remove_nested(structure[digit], targetPath, 
                                       currentPath&digit) 
    end if 
  end if 
  return structure 
end function 
 
------------------------------------------------------------------------------ 

Jean-Marc

new topic     » goto parent     » topic index » view message » categorize

Search



Quick Links

User menu

Not signed in.

Misc Menu