包含“ &&”的拆分Bash字符串

时间:2019-01-08 15:07:18

标签: string bash split ampersand

我有一个像这样的bash脚本:

0: path=/me
1: &
2: you/folder/file.json
3: user=Bob

它产生:

➜  params="path=/me & you/folder/file.json&&user=Bob"
➜  splitParams=(${params//&&/ })
➜  echo $splitParams
path=/me & you/folder/file.json user=Bob

但是当我在shell中输入em时:

0: path=/me & you/folder/file.json
1: user=Bob

我希望脚本的输出就像我在shell中键入时一样:

[√] Flutter (Channel stable, v1.0.0, on Microsoft Windows [Version 10.0.17134.472], locale fa-IR)
    • Flutter version 1.0.0 at C:\Android\flutter
    • Framework revision 5391447fae (6 weeks ago), 2018-11-29 19:41:26 -0800
    • Engine revision 7375a0f414
    • Dart version 2.1.0 (build 2.1.0-dev.9.4 f9ebf21297)

[!] Android toolchain - develop for Android devices (Android SDK 27.0.3)
    • Android SDK at c:\Android\android-sdk
    • Android NDK location not configured (optional; useful for native profiling support)
    • Platform android-28, build-tools 27.0.3
    • ANDROID_HOME = C:\Android\android-sdk
    • Java binary at: C:\Program Files\Android\Android Studio\jre\bin\java
    • Java version OpenJDK Runtime Environment (build 1.8.0_152-release-1024-b02)
    X Android license status unknown.

[√] Android Studio (version 3.1)
    • Android Studio at C:\Program Files\Android\Android Studio
    • Flutter plugin version 29.0.1
    • Dart plugin version 173.4700
    • Java version OpenJDK Runtime Environment (build 1.8.0_152-release-1024-b02)

[√] Connected device (1 available)
    • HUAWEI CUN U29 • CCMBBCB6C0153603 • android-arm • Android 5.1 (API 22)

4 个答案:

答案 0 :(得分:1)

echo $splitParams仅打印第一个元素。使用declare -p来精确查看数组中的内容:

$ declare -p splitParams
declare -a splitParams=([0]="path=/me" [1]="&" [2]="you/folder/file.json" [3]="user=Bob")

那么,现在如何在&&处分割字符串却又没有空格混乱呢?好吧,依靠shell来实现是容易出错的。当输入字符串已经包含空格时,将&&更改为空格并在空格上进行分割会遇到麻烦。

一种更好的方法是将定界符更改为换行符。然后,不要使用array=($string)来使$string分开,而要使用readarray,这样空格就不会触发拆分,而只会触发换行符。

$ readarray -t splitParams < <(sed 's/&&/\n/g' <<< "$params")
$ declare -p splitParams
declare -a splitParams=([0]="path=/me & you/folder/file.json" [1]="user=Bob")

答案 1 :(得分:0)

grep -oP '(?<=^|&&).*?(?=&&|$)' <<< "path=/me & you/folder/file.json&&user=Bob"

打印:

path=/me & you/folder/file.json
user=Bob

答案 2 :(得分:0)

您可以使用以下内容:

params="path=/me & you/folder/file.json&&user=Bob"
while IFS=  read -r -d $'\0'
do
  splitParams+=("$REPLY")
done < <(echo "${params}" | awk -F'&&' '{ for (i=1;i<=NF;i++) printf("%s\0",$i); }')

for i in "${!splitParams[@]}"
do
    echo "$i: ${splitParams[i]}"
done

输出:

0: path=/me & you/folder/file.json
1: user=Bob

答案 3 :(得分:0)

您可以为此目的使用awk,但请记住,在awk外部无法访问splitParams。我们将使用awk的split函数:

  

split([要处理的字符串],[结果数组],[Delimeter]

#!/bin/bash
params="path=/me & you/folder/file.json && user=Bob"
awk -F: '{split($0, splitParams, "&&"); print splitParams[1] "\n"splitParams[2]}' <<< $params

输出:

 path=/me & you/folder/file.json
  user=Bob