linux的awk错误,关于linux:Unix’别名’失败并带有’awk’命令

我在Unix中创建了一个别名,发现以下命令失败了..

alias logspace='find /apps/ /opt/ -type f -size +100M -exec ls -lh {} \; | awk '{print $5, $9 }''

我得到以下内容:

awk: cmd. line:1: {print

awk: cmd. line:1:       ^ unexpected newline or end of string

关于为什么管道awk命令失败的任何想法......

谢谢,

肖恩。

这是因为你在{print ...之前有'关闭你的字符串。 你需要正确地逃避你的报价。

正确的解决方法是将其声明为函数。 logspace () { find /apps /opt -type f -size +100M -exec ls -lh {} \; | awk '{ print $5, $9 }'; }甚至更好地使用find的内置printf格式来提取所需的字段。

跳过答案中提到的引用钩子的另一种方法是使用shell函数而不是别名,如下所示:stackoverflow.com/a/7244626/15109

如果答案解决了您的问题,请单击旁边的大复选标记(?)接受。 如果您发现其他答案有帮助,请向上投票。 接受和提高投票的答案不仅有助于回答,也有助于未来的读者。 请参阅相关的帮助中心文章。 如果您的问题尚未得到完全解答,请提供反馈。

补充@ Dropout的有用答案:

TL;博士

问题是OP尝试在' - 封闭(单引号)字符串中使用'。

在这种情况下,最强大的解决方案是用'\''(原文如此)替换每个内部':

alias logspace='find /apps/ /opt/ -type f -size +100M -exec ls -lh {} \; |

awk '\''{print $5, $9 }'\'''

Bourne-like(POSIX兼容)shell不支持在单引号('...' -enclosed)字符串中使用'字符AT ALL - 甚至不使用转义。

(相比之下,你可以在双引号字符串中以\"的形式转义",并且在@ Droput的回答中,你可以直接嵌入'字符,但是请看下面的陷阱。)

上面的解决方案有效地从多个单引号字符串构建字符串,文字'字符。 - 在单引号字符串之外转义为\' - 被拼接。

另一种方式,正如@Etan Reisinger在评论中所做的那样:'\''意味着:"关闭字符串","逃避单引号","开始新字符串"。

在定义别名时,通常需要围绕其定义使用单引号,以便延迟对命令的评估,直到调用别名为止。

其他解决方案及其缺陷:

以下讨论基于以下别名的替代解决方案:

alias foo='echo A '\''*'\'' is born at $(date)'

注意*如何有效地用单引号括起来 - 使用上述技术 - 以便在以后调用别名时防止路径名扩展。

调用时,此别名打印文字A * star is born,然后打印当时的日期和时间,例如:A * is born at Mon Jun 16 11:33:19 EDT 2014。

使用名为ANSI C引用的功能以及支持它的shell:bash,ksh,zsh

ANSI C引用的字符串,包含在$'...'中,DO允许转义嵌入的'字符。 as \':

alias foo=$'echo A \'*\' is born at $(date)'

陷阱:

此功能不是POSIX的一部分。

通过设计,转义序列如,\t,......也被解释(事实上,这是该功能的目的)。

使用交替引用样式,如@ Dropout的答案:

陷阱:

'...'和"..."具有不同的语义,因此将一个替换为另一个可能会产生意想不到的副作用:

alias foo="echo A '*' is born at $(date)" # DOES NOT WORK AS INTENDED

虽然语法正确,但这不会按预期工作,因为使用双引号会导致shell立即扩展命令替换$(date),从而将别名定义时的日期和时间硬连接到别名中。

如上所述:在定义别名时,通常需要围绕其定义使用单引号,以便延迟对命令的评估,直到调用别名为止。

最后,一个警告:

在类似Bourne的shell环境中,棘手的事情是将'嵌入单引号字符串中 - 有时 - 错误地 - APPEARS工作(而不是产生语法错误,如在问题中),当它改为执行不同的操作时:

alias foo='echo a '*' is born at $(date)'  # DOES NOT WORK AS EXPECTED.

接受此定义(没有语法错误),但不会按预期工作 - 定义的右侧有效地解析为3个字符串 - 'echo a ',*和' is born at $(date)',由于shell如何解析字符串(合并相邻的字符串,引用删除),会产生以下单个字面字符串:a * is born at $(date)。由于*在结果别名定义中未加引号,因此在调用别名时,它将扩展为当前目录(路径名扩展)中所有文件/目录名称的列表。

很高兴听到它的帮助,@ VivekAgrawal。

你可以使用不同的引号来包围整个文本和内部字符串。

尝试将其更改为

alias logspace="find /apps/ /opt/ -type f -size +100M -exec ls -lh {} \; | awk '{print $5, $9 }'"

换句话说,您的外部引号应该与内部引号不同,因此它们不会混合。

是不是关于$?我不得不逃避它在这个例子中工作:alias ip="ifconfig en1 | awk '/inet / { print \$2 }'"

我不得不使用不同的报价来逃避$

在某些情况下,当您混合双引号和单引号时,您会得到奇怪的结果。示例:alias ipconnected ="netstat -tn 2> / dev / null | grep:80 | awk'{print $ 5}'| cut -d:-f1 | sort | uniq -c | sort -nr | head"

社区维基更新:

这个答案的兑换功能是认识到OP的问题在于在字符串内未使用字符串分隔符(')。

但是,这个答案包含一般的字符串处理事实,但并不特别适用于(Bourne-like,POSIX兼容)shell编程,因此不能直接解决OP的问题 - 请参阅注释。

注意:代码片段是伪代码,而不是shell语言。

基本字符串:您不能在字符串中使用相同的引号,因为整个字符串是用以下分隔的:

foo='hello, 'world!'';

^--start string

^-- end string

^^^^^^^^--- unknown"garbage" causing syntax error.

你必须转义内部字符串:

foo='hello, \'world!\'';

^--escape

这对于地球上几乎每种编程语言都是如此。如果它们不提供转义机制,例如\,那么你必须使用其他方法,例如

quotechar=chr(39); // single quote is ascii #39

foo='hello ,' & quotechar & 'world!' & quotechar;

不幸的是,(Bourne-like)shell语言与地球上的其他编程语言不同:你无法逃脱' chars。在' - 封闭的字符串中,=周围不能有空格。

实际上,正如@ mklement0所说,你不能在单引号内逃避单引号。你唯一能做的就是在某处使用双引号或在每个"嵌入式"单引号上使用(非常难看的)'\''序列。 (即"关闭字符串","转义单引号","启动新字符串"。)

以上代码从未打算被视为bash。它是伪代码,用于显示如何在不采取特殊措施的情况下在字符串中使用引号。

@MarcB:问题标记为linux和shell,并使用alias功能,因此我们清楚地讨论类似Bourne的POSIX兼容shell(其中bash)。您的原始答案(a)建议转义,特别是在手头的情况下不是选项,并且(b)在识别该事实时,然后使用不同语言的语法作为解决方法示例。总而言之,从原始问题的角度来看,这个答案主要是分散注意力,并且需要克服所产生的混乱,以便了解它所包含的一般事实。

@MarcB:我已经再次编辑了答案,希望澄清你的原始意图,同时避免分心方面。

转义$符号而不是awk的单引号,并使用双引号作为别名。

试试这个 :

alias logspace="find /apps/ /opt/ -type f -size +100M -exec ls -lh {} \; | awk '{print \$5, \$9 }'"

希望它有效,我不确定alias可以扩展""。让我们知道是否有效。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值