PHP向shell脚本传递类似“数组”格式的数据:模拟场景1计算捆绑商品的价格,捆绑商品包含多个商品,这个商品不确定,我们暂定定义为苹果、栗子、香蕉。价格分别为8元/公斤、10元/公斤、3元/公斤。重量规格设定为500g。我们将价格作为参数传递给shell脚本以计算总价。以下是PHP部分的代码:$prices=array("apple"=>8,"banana"=>3,"chestnut"=>10);$command="bash".ROOT_PATH."/script/test.sh";foreach($pricesas$price){$command.=$price."";}$output=array();$ret=1;exec($command."2>&1",$output,$ret);var_dump($command,$output,$ret);exit;//command命令为://bash/data/home/tina/script/test.sh8310下面是test.sh脚本的内容:#!/bin/bashall=0forpricein$@doall=`expr${all}+${price}`doneecho${all}模拟场景2在场景1的情况下,我们修改价格为浮点数、苹果、板栗、香蕉价格分别为8.8元/公斤、9.9元/公斤、3.5元/公斤。expr表达式会报错(expr:参数个数错误),expr不支持浮点类型。在这里,应该使用bc或awk。shell脚本修改如下:#!/bin/bashall=0forpricein$@do#all=$(echo${price}+${all}|bc)all=$(awk"BEGIN{print${all}+${price}}")doneecho${all}模拟场景3是在场景2的基础上,现在需要改变捆绑商品的权重。苹果0.5KG,香蕉1KG,栗子1.5KG。在计算价格时,我们还需要将权重参数传递给shell脚本,来计算价格方案一:在脚本后面继续添加这些参数,参数个数一分为二。我们知道前半部分是价格参数,后半部分是权重参数。修改如下:PHP代码部分:$prices=array("apple"=>8.8,"banana"=>3.5,"chestnut"=>9.9);$weights=array("apple"=>1,"banana"=>2,"chestnut"=>3);$command="bash".ROOT_PATH."/script/test.sh";foreach($pricesas$price){$command.=$price."";}foreach($weightsas$weight){$command.=$weight."";}$output=array();$ret=1;exec($command."2>&1",$output,$ret);var_dump($command,$output,$ret);exit;//命令命令为://bash/data/home/tina/script/test.sh8.83.59.9123修改后的shell脚本为:#!/bin/bashall=0count=`expr${#}/2`countIndex=`expr${count}+1`forpricein${@:1:${count}}do#all=$(echo"${price}*${!countIndex}+${all}"|bc)all=$(awk"BEGIN{print${all}+${price}*${!countIndex}}")countIndex=`expr${countIndex}+1`doneecho${all}方案二:将这两类数据分组,类似于PHP数组。这样在命令中每组参数都需要用单引号括起来,这样shell会认为只有两个参数,然后在shell脚本中把它们当作一个数组。,修改如下:PHP部分:$prices=array("apple"=>8.8,"banana"=>3.5,"chestnut"=>9.9);$weights=array("苹果"=>1,"香蕉"=>2,"栗子"=>3);$command="bash".ROOT_PATH."/script/test.sh'";//添加单引号foreach($pricesas$price){$command.=$price."";}$命令=修剪($命令)。“''”;//添加单引号foreach($weightsas$weight){$command.=$weight."";}$command=trim($command)."'";//添加单引号$output=array();$ret=1;exec($command."2>&1",$output,$ret);var_dump($command,$output,$ret);exit;//命令指令为://bash/data/home/tina/script/test.sh'8.83.59.9''123'shell脚本修改为:#!/bin/bashall=0index=0prices=(${1})weights=(${2})forpricein${prices[@]}doall=$(awk"BEGIN{print${price}*${weights[${index}]}+${all}}")index=`expr${index}+1`doneecho$all相比方案一和方案二,从长远来看,个人认为方案二更占优势,容易区分:可以清楚的知道第一个参数是价格组,第二个参数是权重组,可以展开:比如一个折扣率参数(折扣率分别是0.9、0.88、0.95)会是后期添加,优惠券价格减5元等;这个计数的值是不固定的,折扣率的计算,假设每种水果都有单独的折扣率,计数还是3的倍数,除以2可以改为除以3。#command命令为:bash/data/home/tina/script/test.sh8.83.59.91230.90.880.95但是对于coupons来说,一定是这个捆绑商品的整体折扣,是单个参数,假设coupon是5元,继续加参数#command命令为:bash/data/home/tina/script/test.sh8.83.59.91230.90.880.955这个时候不好区分。一连串的数字不利于后续维护。接手的人肯定是一头雾水,这都是什么参数,然后心里就开始吐槽了。想了想方案,我也可以修改count=(参数个数-1)/3,但是后面如果有其他需求,这个逻辑就需要修改了,这很烦人。对于第二种方案,不需要修改之前的逻辑,直接添加即可。之前的逻辑不用修改,脚本也不会写。这只是一个栗子。当我第一次看到剧本时,我惊呆了。这个场景也是模拟的。其实就是处理大量的大文件,然后学着看了,发现这些命令超...怎么说呢?感觉发现了一个新世界,功能强大。。。记录一下我第一次写shell脚本,嗯,就这个酱(emmmmm。。脚本不容错)。。。加几个简单的命令学会了,别忘了......1dos2unix将Windows下文件中的换行键转换成Unix下的换行键(可以用Notepad++编辑器看到window下的换行符是CRLF,andUnix下的换行符是LF)2按照指定的Sortingbyrules对文件进行排序3comm比较两个排序后的文件,可以得到差值和交集(功能很强大,然后这两个文件一定是顺序,否则会报错,是前面sort命令排序的文件)4wc统计文件行数(其实就是统计换行符)5$@脚本的所有参数6$#脚本参数个数7${@:1:4}指的是脚本参数从1到4(可以范围选择行动)
