4

I have a file that contains a list:

line1
line2
line3
.
.
.

I want to join everything in a string in bash like so:

"line1", "line2", "line3", ...... (no comma at the end)

How do I do that?

Edit: This is not a duplicate of How to join multiple lines of file names into one with custom delimiter? because I am trying to get every item in double quotes while joining.

Community
  • 1
  • 1
Iokanaan Iokan
  • 704
  • 3
  • 12
  • 26
  • Do you want to merge the lines in another file or in a variable in your script? – Fred Jan 30 '17 at 15:07
  • Output will go into a second file. – Iokanaan Iokan Jan 30 '17 at 15:08
  • Yours is still a duplicate; if you need help figuring out how to wrap each line in double quotes before joining, that's a separate question (but also [a duplicate](http://stackoverflow.com/questions/6554066/how-to-enclose-every-line-in-a-file-in-double-quotes-with-sed)). – tripleee Jan 31 '17 at 04:48

4 Answers4

6

For an input file like

line1
line2
line3

I would use sed and tr as follows:

$ sed 's/.*/"&"/;$!s/$/, /' infile | tr -d '\n'
"line1", "line2", "line3"

The first sed command quotes every line; the second one adds , at the end of every line except the last (the $! address: "not the last line").

tr then removes all linebreaks.

If you want to do it completely in Bash:

#!/usr/bin/env bash

mapfile -t arr < infile               # Read file into array
arr=("${arr[@]/#/\"}")                # Prepend " to each element
arr=("${arr[@]/%/\"}")                # Append " to each element
IFS=,                                 # Set separator to comma
str="${arr[*]}"                       # Comma separated string
printf '%s\n' "${str//\",\"/\", \"}"  # Insert space after commas
Benjamin W.
  • 46,058
  • 19
  • 106
  • 116
3

Using awk:

$ awk '{ printf "%s\"%s\"", (NR==1?"":", "), $0 } END{ print "" }' file
"line1", "line2", "line3"
James Brown
  • 36,089
  • 7
  • 43
  • 59
2

Lets say that you file name is test then this will do the trick

  while IFS= read -r i; do echo " \"$i\""; done < test | paste -sd "," |sed 's/ //1'
chepner
  • 497,756
  • 71
  • 530
  • 681
Mitesh Pant
  • 524
  • 2
  • 15
1

Building a general solution to most problems of this kind.
Using a general start, middle and end string

A solution with only bash:

#!/bin/bash

infile="infile"
start='"'
middle='", "'
end='"'

res="$start"                             # start the result with str "$start".
while  IFS=$'\n' read -r line            # for each line in the file.
do     res="${res}${line}${middle}"      # add the line and the middle str.
done   <"$infile"                        # for file "$infile"
res="${res%"$middle"}${end}"             # remove "$middle" on the last line.
printf '%s\n' "${res}"                   # print result.

And a solution for larger files with awk:

#!/bin/bash

infile="infile"
start='"'
middle='", "'
end='"'

awk -vs="$start" -vm="$middle" -ve="$end" '
BEGIN{printf("%s",s)}
{
if(ll){printf("%s%s",ll,m)}
ll=$0
}
END{printf("%s%s%s",ll,e,"\n")}
' "$infile"