代码之家  ›  专栏  ›  技术社区  ›  user3742796

如何在键之间均匀分布总值数

  •  2
  • user3742796  · 技术社区  · 7 年前

    如何在键之间均匀分布值的总数。

    我正在尝试将值均匀分布到关键点。我不希望值vcn[01-05]和vcn[06-10]分别位于vsn01和vsn02键下。相反,我希望vcn[01,03,05,07,09]和vcn[02,04,06,08,10]分别位于vsn01和vsn02键下。

    例如

    值的数目:-

    vcn01
    vcn02
    vcn03
    vcn04
    vcn05
    vcn06
    vcn07
    vcn08
    vcn09
    vcn10
    

    钥匙

    vsn01
    vsn02
    

    所需输出

    vsn01
    
    vcn01
    vcn03
    vcn05
    vcn07
    vcn09
    
    vsn02
    
    vcn02
    vcn04
    vcn06
    vcn08
    vcn10 
    

    注:-

    钥匙总数-20,即vsn[01-20]

    数值总数-100,即vcn【01-100】

    已尝试:-

    #! /bin/bash
    
    
    function create_vsn_vcn_lists ()
    {
        pnode_cnt=$1
        vcn_cnt=$2
    
        declare -a vcn_lists
        for i in `seq $pnode_cnt`; do
            ${vcn_lists[${i}]}=''
        done
    
        for i in `seq $vcn_cnt`; do
            for j in `seq $pnode_cnt`; do
                ret=`expr ${i} % ${j}`
                if [ $ret -eq 0 ]; then
                    ${vcn_lists[${j}]}="${vcn_lists[${j}]} vcn${i}"
                fi
            done
        done
    
        for i in `seq $pnode_cnt`; do
            echo ${vcn_lists[${j}]}
        done
    
    }
    
    create_vsn_vcn_lists 2 20
    
    3 回复  |  直到 7 年前
        1
  •  1
  •   Ed Morton    7 年前

    看见 https://unix.stackexchange.com/questions/169716/why-is-using-a-shell-loop-to-process-text-considered-bad-practice 对于 一些 您不应该尝试在shell中像这样操纵文本的原因。编写shell的人也为shell编写了awk来调用来操纵文本,所以就使用它吧。

    如果您的输入仅为您发布的脚本中显示的2个数字( create_vsn_vcn_lists ):

    $ cat tst.awk
    BEGIN {
        for (keyNr=1; keyNr<=numKeys; keyNr++) {
            printf "vsn%02d\n\n", keyNr
            for (valNr=keyNr; valNr<=numVals; valNr+=numKeys) {
                printf "vcn%02d\n", valNr
            }
            print ""
        }
    }
    

    $ awk -v numKeys=2 -v numVals=10 -f tst.awk
    vsn01
    
    vcn01
    vcn03
    vcn05
    vcn07
    vcn09
    
    vsn02
    
    vcn02
    vcn04
    vcn06
    vcn08
    vcn10
    

    或者如果您的输入是两个独立的文件,就像您发布的示例输入中显示的那样( number of values keys ):

    $ cat tst.awk
    NR==FNR {
        keys[++numKeys] = $0
        next
    }
    {
        keyNr = ((FNR-1) % numKeys) + 1
        vals[keyNr] = (keyNr in vals ? vals[keyNr] ORS : "") $0
    }
    END {
        for (keyNr=1; keyNr<=numKeys; keyNr++) {
            print keys[keyNr] ORS ORS vals[keyNr] ORS
        }
    }
    

    $ awk -f tst.awk keys values
    vsn01
    
    vcn01
    vcn03
    vcn05
    vcn07
    vcn09
    
    vsn02
    
    vcn02
    vcn04
    vcn06
    vcn08
    vcn10
    
        2
  •  0
  •   RavinderSingh13 Nikita Bakshi    7 年前

    你能试试下面的吗 awk 如果这对你有帮助,请告诉我。

    awk -v count=$(wc -l < keys) 'FNR==NR{a[++i]=$0;next} {b[FNR]=$0} END{for(k=1;k<=count;k++){print b[k] ORS;for(j=k;j<=i;j+=count){print a[j]};print "********"}}' number_of_values keys
    

    在这里也添加了一个非线性形式的解决方案。

    awk -v count=$(wc -l < keys) '
    FNR==NR{
      a[++i]=$0;
      next}
    {
      b[FNR]=$0
    }
    END{
      for(k=1;k<=count;k++){
         print b[k] ORS;
      for(j=k;j<=i;j+=count){
         print a[j]};
         print "********"}
    }
    ' number_of_values keys
    

    说明: 在此处也添加代码解释。

    awk -v count=$(wc -l < keys) '  ##Creating a variable named count whose value is the number of lines in Input_file named keys.
    FNR==NR{                        ##Checking condition here if FNR==NR which will be TRUE when first Input_file is being read.
      a[++i]=$0;                    ##Creating an array named a whose index is variable i whose value is getting incremented each time with 1 and value is current line.
      next}                         ##next keyword will skip all further statements from here on wards, since we do not want to execute them now.
    {
      b[FNR]=$0                     ##This statement will be executed when 2nd Input_file named keys is being read. Creating array named b whose value is $0 with index FNR.
    }
    END{                            ##Starting END section of awk here now.
      for(k=1;k<=count;k++){        ##Starting a for loop whose value starts from k=1 to till value of variable count.
         print b[k] ORS;            ##Printing the value of array b whose index is k and ORS whose default value is new line.
      for(j=k;j<=i;j+=count){       ##Starting a for loop here which starts from j=k to till value of variable i and increment happens with count variable increment.
         print a[j]};               ##Printing value of array a whose index is variable j.
         print "********"}          ##Printing ******** here to segregate between different output sets.
    }
    ' number_of_values keys         ##Mentioning the Input_file names here.
    
        3
  •  0
  •   CrazyApe84    7 年前

    这个怎么样?

    #!/bin/bash
    
    function create_vsn_vcn_lists {
        local vsn_cnt=$1 vcn_cnt=$2 start=1 i j
        for ((i=1; i<=vsn_cnt; ++i, ++start)); do
            printf "vsn%02d\n\n" $i
            for ((j=start; j<=vcn_cnt; j+=vsn_cnt)); do
                printf "vcn%02d\n" $j
            done
            echo
        done
    }
    
    create_vsn_vcn_lists 3 10
    

    输出:

    vsn01
    
    vcn01
    vcn04
    vcn07
    vcn10
    
    vsn02
    
    vcn02
    vcn05
    vcn08
    
    vsn03
    
    vcn03
    vcn06
    vcn09