vimscript – ¿Cómo puedo fusionar dos diccionarios en Vim?

Pregunta:

Tengo dos dictados:

:let defaults = {'hello': 'world', 'bye': 'jupiter'}

:let override = {'hello': 'mars'}

¿Cómo puedo fusionar las claves de override para terminar con un nuevo dictado así:

{'hello': 'mars', 'bye': 'jupiter'}

Respuesta:

Puede usar extend() :

:let defaults = {'hello': 'world', 'bye': 'jupiter'}
:let override = {'hello': 'mars'}

:echo extend(defaults, override)
{'hello': 'mars', 'bye': 'jupiter'}

Las claves del segundo argumento anulan las existentes en el primero. El dictado de defaults se modificará en su lugar , lo que puede no ser deseable. Utilice copy() para evitar que:

:call extend(copy(defaults), override)
:echo defaults
{'hello': 'world', 'bye': 'jupiter'}

Esto es especialmente algo con lo que hay que tener cuidado cuando se pasa un dictado a una función, ya que se pasa por referencia (por lo que también se modificará fuera de la función).


Tenga en cuenta que no fusionará dictados anidados, lo que puede ser bueno o no, dependiendo de lo que esté buscando:

:echo extend({'nest': {'a': 'b'}}, {'nest': {'b': 'XXXX'}})
{'nest': {'b': 'XXXX'}}

Necesitará una pequeña función auxiliar para fusionar de forma recursiva dictados anidados:

" Merge two dictionaries, also recursively merging nested keys.
"
" Use extend() if you don't need to merge nested keys.
fun! s:merge(defaults, override) abort
  let l:new = copy(a:defaults)
  for [l:k, l:v] in items(a:override)
    let l:new[l:k] = (type(l:v) is v:t_dict && type(get(l:new, l:k)) is v:t_dict)
          \ ? s:merge(l:new[l:k], l:v)
          \ : l:v
  endfor
  return l:new
endfun

Puede eliminar la copy() si desea modificarla en el lugar (un poco más rápido, pero posiblemente inesperado).

Leave a Comment

Your email address will not be published.

Scroll to Top

istanbul avukat

-

web tasarım