Bash脚本中获取sol3-script-ui进程数与命令行结果不符的原因及解决方法
Let's break down what's happening here, and how to fix it to get the correct 8 count in your script.
The Problem
When you run the ps aux | grep ... pipeline directly in your terminal, you get the correct 8 processes matching sol3-script-ui. But when you wrap this exact command in a bash script, the output jumps to 10. What's causing this discrepancy?
Root Cause
The extra 2 counts come from processes spawned by your script itself that get caught by your grep filter:
- The bash process running your script: Its command line is
/bin/bash ./get-sol3-script-ui-nr.sh, which includes the string "sol3-script-ui" — so your grep picks it up as a match. - The
grep "sol3-script-ui"process from your pipeline: Even though you addedgrep -v grepto exclude grep processes, this only filters out lines containing the word "grep". The grep process's command line still has "sol3-script-ui", so it gets matched before the exclusion step.
Together, these two unintended matches add 2 to your original 8, resulting in the incorrect 10 count.
Fixes to Get the Correct Count
1. Use pgrep (The Easiest, Most Reliable Way)
pgrep is purpose-built for counting processes by their actual executable name, and it automatically ignores the script and grep processes (since it doesn't match command line arguments, just the process name).
Update your script to this:
#!/bin/bash sol3Nr=$(pgrep -c sol3-script-ui) echo $sol3Nr
This will consistently return the correct 8 count without any extra noise.
2. Tweak Your Grep Pattern
If you want to stick with your original pipeline, use a regex trick to avoid matching the grep process itself:
#!/bin/bash sol3Nr=$(ps aux | grep "[s]ol3-script-ui" | grep -v grep | awk '{print $2}' | wc -l) echo $sol3Nr
The [s] tells grep to match the letter s, so it still finds your target sol3-script-ui processes. But the grep process's command line will be grep "[s]ol3-script-ui" — which doesn't contain the exact string "sol3-script-ui", so it won't be matched. For extra safety, you can add a filter to exclude the script itself:
#!/bin/bash sol3Nr=$(ps aux | grep "[s]ol3-script-ui" | grep -v grep | grep -v "get-sol3-script-ui-nr.sh" | awk '{print $2}' | wc -l) echo $sol3Nr
This works, but it's more fragile than using pgrep.
3. Use ps Built-In Filtering
You can cut out grep entirely by using ps's native process filtering:
#!/bin/bash sol3Nr=$(ps -C sol3-script-ui --no-headers | wc -l) echo $sol3Nr
The -C sol3-script-ui flag tells ps to only show processes named sol3-script-ui, and --no-headers removes the top header line so wc -l counts only the actual process lines.
内容的提问来源于stack exchange,提问作者XYZ

