Использование вложенного цикла for Напишите сценарий bash для проверки соответствия символов и типа данных в любых двух записях поля

Образец данных:

Header | <Transaction_ID> | <Item_ Name> |<Item_Type> | <Customer_ID> | <Type_of_Transaction> | <Payment_Method>|Amount

Data |1001 |Samsung |Handset |R2R003 |Online |Credit Card |100|

Data | 1004|LG |TV | R2R042| Online | Debit card|150.24|

Trailer | 2

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

Требование:

Необходимо использовать вложенный цикл for для проверки любых двух или трех записей поля.

Я попробовал этот код ниже, но он отлично работает для записей одного поля.

!# /bin/bash 

now=`date +"%d_%m_%y" ` 

file=transaction${now}.dat.gz 

#header_fieldc is a parameter which has each header fields in new line 

header_fieldc=`zcat $file | head -1|tr "|" "\n" ` 

a=( $header_fieldc) 

for (( i=0; i<=${#a[@]}; i++ ));do 
 
  echo "${a[i]}" 
 
  if [ $i == 0 ];then 
  
    i=`expr $i + 1 ` 
    rec_fieldc=`zcat $file |sed'1d;$d' 
    |cut -d\| -f $i `
  
  fi 
  #rec_fieldc parameter contains records of ith header field .
 
  b=( $rec_fieldc )
 
   for (( j=0; j<=${#b[@]}; j++ ));do 
         
          echo "${b[j]}" 
         
          var=`echo "${b[j]}" ` 
         
          if [[ "${var}" =~ ^[0-9]+$ ]];then 
               echo " ${b[j]} valid" 
        
           else 
                 echo "invalid character precent in ${a[j]} field" >exception.txt 
                 exit 0 
           fi 
   done
 
done

Выход:

<TransactionID> 

1001 is a valid record 

1004 is a valid record
Стоит ли изучать PHP в 2023-2024 годах?
Стоит ли изучать PHP в 2023-2024 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Приемы CSS-макетирования - floats и Flexbox
Приемы CSS-макетирования - floats и Flexbox
Здравствуйте, друзья-студенты! Готовы совершенствовать свои навыки веб-дизайна? Сегодня в нашем путешествии мы рассмотрим приемы CSS-верстки - в...
Тестирование функциональных ngrx-эффектов в Angular 16 с помощью Jest
В системе управления состояниями ngrx, совместимой с Angular 16, появились функциональные эффекты. Это здорово и делает код определенно легче для...
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
2
0
103
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий

ПРИМЕЧАНИЕ: не забывайте, что операторы if используют == для сравнения, а не =, иначе я думаю, что ваш код может работать, если вы исправите это.

Я воспроизвел установку так. Я добавил несколько строк, в которых больше/меньше полей для демонстрации. Содержимое файла sample_data.txt:

Header | <Transaction ID> | <Item Name> |<Item Type> | <Customer ID> | <Type of Transaction> | <Payment Method>| Amount
Data |1001 |Samsung |Handset |R2R003 |Online |Credit Card |100|
Data |1001 |Samsung |Handset |R2R003 |Online |extra |Credit Card |100|
Data |1001 |Samsung |Online |Credit Card |100|
Data | 1004|LG |TV | R2R042| Online | Debit card|150.24|
Data |1001 |Samsung |Handset |R2R003 |Online |extra |Credit Card |100|
Trailer | 2

Вот скрипт test.sh:

#!/bin/bash
header_field_count=$(cat sample_data.txt | awk -F '|' '{print NF}' |head -1)
echo 'header_field_count:' $header_field_count
number_of_lines=$(wc -l < sample_data.txt)
echo 'number of lines to process in file:' $number_of_lines
let current_line=2 #skip 1st line because that is header
data_field_count_array=($(cat sample_data.txt | awk -F '|' '{print NF -1}')) # note NF -1 because these lines have an extra separator at the end
while [ $current_line -lt $number_of_lines ]; do
  echo 'line:' $current_line 'has' ${data_field_count_array[$current_line-1]} 'fields' #bash arrays are zero indexed therefore the -1 (line 1 is index 0)
  if [[ ${data_field_count_array[$current_line-1]} == $header_field_count ]]; then
    echo 'EQUAL to the Header'
  else
    echo 'NOT EQUAL to the Header'
  fi
  let current_line+=1
done
# this will print any duplicate lines in the sample data
echo -n 'duplicate lines: '
echo $(sort sample_data.txt  | uniq -d)

при запуске это вывод:

header_field_count: 8
number of lines to process in file: 6
line: 2 has 8 fields
EQUAL to the Header
line: 3 has 9 fields
NOT EQUAL to the Header
line: 4 has 6 fields
NOT EQUAL to the Header
line: 5 has 8 fields
EQUAL to the Header
duplicate lines: Data |1001 |Samsung |Handset |R2R003 |Online |extra |Credit Card |100|

он будет работать с любым количеством строк данных

Вы можете провести дополнительное исследование и добавить больше примеров проверки, чтобы проверить, являются ли поля допустимыми числами. См.: Как проверить, является ли переменная числом в Bash?

Пример проверки типов символов: вы можете поиграть с этим скриптом, вызвав его:

./script.sh Test this string for me пройдет проверку строки

./script.sh -187.8 пройдет проверку номера

#!/bin/bash
#regex example
echo 'testing string:"'$@'"'
re='^[0-9 -.]'     #number digits and negative or decimal allowed
if ! [[ $@ =~ $re ]]; then #compare input with the allowed character regex
  echo 'not a decimal or negative number'
fi
re='^[a-z ,]'     #lower case letters and SPACE COMA allowed
if ! [[ $@ =~ $re ]]; then
  echo 'not a lowercase string with SPACE or COMA'
fi
re='^[a-zA-Z ,.;]' #lower and uppercase letters and SPACE COMA DOT SEMICOLON allowed
if ! [[ $@ =~ $re ]]; then
  echo 'not a text string'
fi

Вы можете добавить любые символы, такие как @, в скобки, если хотите проверить электронную почту или что-то в этом роде.

Это последнее редактирование (вопрос слишком углублён в детали)

#!/bin/bash
header_field_count=$(cat sample_data.txt | awk -F '|' '{print NF}' |head -1)
echo 'header_field_count:' $header_field_count
number_of_lines=$(wc -l < sample_data.txt)
echo 'number of lines to process in file:' $number_of_lines
let current_line=2 #skip 1st line because that is header
data_field_count_array=($(cat sample_data.txt | awk -F '|' '{print NF -1}')) # note NF -1 because these lines have an extra separator at the end
while [ $current_line -lt $number_of_lines ]; do
  echo 'line:' $current_line 'has' ${data_field_count_array[$current_line-1]} 'fields' #bash arrays are zero indexed therefore the -1 (line 1 is index 0)
  if [[ ${data_field_count_array[$current_line-1]} == $header_field_count ]]; then
    echo 'EQUAL to the Header'
  else
    echo 'NOT EQUAL to the Header'
  fi
  let current_line+=1
done
fieldstocheck=("Amount" "<Item Name>")  #name of fields to check; array may be expanded
fieldtypecheck=("num" "string")     #we specify the check requirements (customer ID needs to be a number and so on)
#find which field index in each row corresponds to fieldstocheck
for i in $(seq 1 1 $header_field_count) ; do
  field=$(cat sample_data.txt | head -1 | awk -F '|' '{print $'$i'}')
  let finalindex=${#fieldstocheck[@]}-1
  for j in $(seq 0 1 $finalindex); do
    if [[ "$field" =~ "${fieldstocheck[j]}" ]]; then
      echo $field '==' ${fieldstocheck[j]} 'at index:' $i
      fieldstocheck[j]=$i
    fi
  done
done

#check the column entries if they are valid
let finalindex=${#fieldstocheck[@]}-1
for i in $(seq 0 1 $finalindex); do
  echo $i
  echo 'column' "${fieldstocheck[$i]}" 'needs to be a' "${fieldtypecheck[$i]}"
  fieldlist=("$(cat sample_data.txt | awk -F '|' '{print $'${fieldstocheck[$i]}'}')")
  for j in ${fieldlist[@]}; do
    case "${fieldtypecheck[$i]}" in
      num)
        re='^[0-9 -.]'     #number digits and negative or decimal allowed
        if [[ "$j" =~ $re ]]; then
          echo 'OK number' $j
        else
          echo 'ERROR not a decimal or negative number' $j
        fi
      ;;
      string)
        re='^[a-zA-Z ,.;]' #lower and uppercase letters and SPACE COMA DOT SEMICOLON allowed
        if [[ "$j" =~ $re ]]; then
          echo 'OK string' $j
        else
          echo 'ERROR not a string' $j
        fi
      ;;
      *)
        echo 'not valid variable type'
      ;;
    esac
  done
done

Код Ur отлично работает только для подсчета полей в одной записи, но я хочу сравнить поле заголовка с количеством полей каждой записи data_record, для этого нам нужно использовать цикл for, как я пытался выше, но получаю ошибку для кода, упомянутого выше.

NAVYA K N 09.01.2023 16:15

Что эта строка пытается сделать? if [ "${data_fields}" -eq "${i}" ] вы сравниваете строку с числом...

Gerge 09.01.2023 17:05

тоже ошибка cat sampl_data.txt должна быть cat sample_data.txt

Gerge 09.01.2023 17:15

Я создал полный скрипт, проверьте, нужен ли он вам.

Gerge 09.01.2023 18:42

Не могли бы вы сказать мне, как проверить символы действительны или нет для каждого поля.

NAVYA K N 10.01.2023 03:02

Пожалуйста, отредактируйте свой вопрос, если вы хотите получить более конкретный ответ. Я не знаю, о каких «символах» и «действительном» вы говорите, если вы не укажете это в своем вопросе. В противном случае отметьте правильный ответ галочкой, если он работает.

Gerge 10.01.2023 11:29

Я отредактировал вопрос в соответствии с моей просьбой, пожалуйста, просмотрите его один раз

NAVYA K N 11.01.2023 05:08

Если я правильно понимаю, вы хотите проверить одинаковые строки. (иначе, если 2 строки данных совпадают). Невозможно проверить, что правильно, а что нет. Невозможно проверить, например, item name, если у вас нет списка допустимых имен элементов для проверки. Лучшее, что я могу сделать, это проверить числа и строки, value и transaction ID должны быть числом.

Gerge 12.01.2023 19:10

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

Gerge 12.01.2023 20:17

Я отметил ваш ответ. Но, Гердж, я думаю, вы не поняли второй вопрос, который я обновил, говоря о проверке записей и количестве полей. Но я говорю о символах, предположим, что в таблице emp есть столбец идентификатора электронной почты, их единственный @ и точечные символы действительны, а все остальные специальные символы недействительны, это то, что мне нужно проверить по крайней мере для любых двух полей.

NAVYA K N 15.01.2023 04:54

Хорошо, это намного яснее. Я добавил примеры для этого в ответ по ссылке, которую я дал.

Gerge 16.01.2023 14:10

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

NAVYA K N 18.01.2023 17:28

Другие вопросы по теме