perl, заполняющий хэш из вызова подпрограммы при вводе файла, вводе массива или без ввода

#perl #class #hash #subroutine

#perl #класс #хэш #подпрограмма

Вопрос:

Я создал класс следующим образом:

 package Tool;

sub new {

  my ( $class, %args ) = @ARG;

  my $self = bless {
  #hash reference  
    _ToolParameters => { }

  }, $class;

  return $self;

}
 

Затем я хочу создать экземпляр этого класса:

 my $Object = Tool->new();
 

затем я хотел бы прочитать текстовый файл или массив, чтобы заполнить хэш и вызвать его следующим образом:

 from an array:    $Object->ImportData(@Arraylist);
from a textfile:  $Object->ImportData(textfile.csv);
 

в этой функции ImportData я хотел бы прочитать свой ключ из списка массивов, который будет строго иметь идентификатор #, или из файла CSV, это будет строго первый столбец, который является идентификатором # или иметь возможность вставлять значения вручную:

* Я хочу, чтобы он был таким, чтобы идентификатор # = ключ.

Я подумываю также сгенерировать по крайней мере одно поле параметра для этого ключа по умолчанию и присвоить ему значение по умолчанию 0.

В принципе, когда я вернусь из этого списка, у меня будет что-то, предложенное икегами ранее, например:

 $self->{_ToolParameters}{$ID#1}{test_parameter_1} = $value;
$self->{_ToolParameters}{$ID#2}{test_parameter_1} = $value;
 

Если я принимаю массив, входные данные выглядят следующим образом:

 @Arraylist = (key1 ,..., keyN);
 

поскольку это часть более крупной программы, я планирую запускать каждый ключ через серию из нескольких наборов тестов ‘X’, этим наборам тестов я планирую присвоить имя «parameterX», X — номер набора тестов. Я беру первый набор тестов как заданный, поэтому мой желаемый результат должен быть таким, какой у объекта у меня был бы по умолчанию (прежде чем нажимать на какие-либо дополнительные параметры):

 *the default value for the 'value' is zero, because I have not run the testsuite, I am just initializing the field

key1 -> first_test ->0
key2 -> first_test ->0
.
.
keyN ->     first_test ->            0
(key)  (test_parameter_1)  (value of test_parameter_1)
 

Я хочу, чтобы это возвращалось объекту, чтобы я мог позже передать больше тестов в хэш, например, я могу иметь:

 key1 -> first_test -> 0
     -> second_test -> 0
 

Аналогично, из текстового файла все, что меня волнует, — это столбцы, которые представляют ключи или идентификаторы.

Я предполагаю, что мое замешательство заключалось в том, как сделать это назначение надежным, чтобы у меня был объект, содержащий список расширяемых пар значений, но написание этого помогло мне решить большую часть этого.

Вот тут-то мне и требуется некоторое руководство.

 sub ImportData{
 my $a = shift;

 if($a eq /*.csv$/i )
{ #textfile case

  my @get_first_col = some kind of column dump; #keys, probably a while loop

  foreach $key (@get_first_col)
  {
  push($self->{_ToolParameters}{$key}{test_parameter_1} = 0);
  }
}
elseif($a)
{ #array case - want to reliably check if we're handling an array
  foreach (@{a})
  {
  push($self->{_ToolParameters}{$_}{test_parameter_1} = 0);
  }
}
else
{#case of manual input
my $a = <STDIN>
push($self->{_ToolParameters}{$_}{test_parameter_1} = 0);
}

}
 

Комментарии:

1. Можете ли вы показать структуру данных, которую вы хотите получить?

2. Почему бы не сделать одно из полей объекта хэшем , который сопоставляется $key с [$parameter, $parameter2] ?

3. покажите входной текстовый файл (его краткий пример). У @ikegami есть, для ответа просто нужны некоторые реальные входные данные

4. Я видел, что вы обновили свой вопрос, но вы сделали его еще более запутанным (например, сказав, что у вас есть только $key , но вы хотите использовать $ID и $value ). Я повторяю: покажите свои входные данные или желаемый результат для этих входных данных. Я продемонстрировал, как это сделать в моем ответе. Отметьте меня в комментарии, когда вы это сделаете, и я обновлю свой ответ.

5. @ikegami, я думаю, я смог предоставить то, что вы просили, это разумный подход? Делает ли это то, что я думаю, что он делает? Затем я запущу несколько тестовых примеров в своей среде, чтобы увидеть.

Ответ №1:

Непонятно, чего вы хотите.

Для получения

 {
    key1 => {
        parameter1 => 0,
        parameter2 => 0,
    },
    key2 => {
        parameter1 => 0,
        parameter2 => 1,
    },
}
 

учитывая

 my @rows = (
    [ 'key1', 0, 0 ],
    [ 'key2', 0, 1 ],
);
 

ты хочешь

 $self->{$key}{parameter1} = $parameter;
$self->{$key}{parameter2} = $parameter2;
 

или

 $self->{_ToolParameters}{$key}{parameter1} = $parameter;
$self->{_ToolParameters}{$key}{parameter2} = $parameter2;
 

Комментарии:

1. вот как это сделать, но я уверен, что если / когда OP предоставит реальные входные данные, они будут обновлены, чтобы отразить их.

2. Было бы неплохо взять ключ в качестве удостоверения личности#

3. Было бы неплохо использовать ключ в качестве идентификатора #, затем для идентификатора # установить параметр типа «test_one_passed», затем присвоить ему значение begin = 0, но текстовый файл или входные данные будут содержать только идентификатор #, и по умолчанию я бы начал только с этого «test_one_passed», но позже заполните хэш таким образом, чтобы идентификатор должен был пройти больше тестов.

4. Понятия не имею, что ты имеешь в виду. Видите, как я предоставил входные данные и желаемые результаты? Отредактируйте свой вопрос, чтобы предоставить правильные версии этих.