Як грепнути на вихідний код без лову коментарів


10

Я шукаю спосіб присвоїти вихідний код, не маючи іноді помилково-позитивного через коментарі. Наприклад, якщо я шукаю foo у цьому вихідному коді .c:

/* 
 * foo has changed [...] and is now a 2-parameters function
 */
// foo(24)
foo(42, 28);

Наївний grepзнайде 3 випадки, де я хочу лише одне. Я бачив такий спосіб зробити це в StackOverflow, але це не відповідає моїм потребам: PHP недоступний на платформі. Я також знайшов такий спосіб для однорядкових коментарів, але це вирішує лише частину моєї проблеми.

Мені потрібно використовувати класичні інструменти сценаріїв (awk, sed, bash, grep тощо), і мені потрібно, щоб він був швидким, навіть якщо є тисячі файлів.

Чи є зараз, якщо і як можна присвоїти вихідний код та лише вихідний код?


3
Створення таблиці тегів може бути кращим підходом, залежно від того, що ви робите.
Жил "ТАК - перестань бути злим"

Відповіді:


10

Ви можете спробувати наївний підхід, щоб відповідати таким коментарям:

 $ egrep -v "^(//|/\*| \*)" sourcecode

Це буде тільки зворотний матч з префіксами коментарів - це рядки , що починаються з будь- //, /*, *або */- і , отже, не поїду з блоків, які закоментовані з /*і */парою.


Злегка змінено для роботи з відступними коментарями: $ egrep -v "^ [[: space:]] * ((// | / * | *)" вихідний код
mbonness

11

grep працює над чистим текстом і нічого не знає про базовий синтаксис вашої програми C. Тому, щоб не шукати всередині коментарів, у вас є кілька варіантів:

  1. Стріпте С-коментарі перед пошуком, ви можете це зробити, використовуючи gcc -fpreprocessed -dD -E yourfile.cДеталі, див. Https://stackoverflow.com/questions/2394017/remove-comments-from-cc-code

  2. Напишіть / використовуйте декілька химерних напівробочих сценаріїв, як ви вже знайшли (наприклад, вони працюють, пропускаючи рядки, починаючи з //або /*), щоб обробити деталі всіх можливих коментарів C / C ++ (ще раз перегляньте попереднє посилання для деяких страшних тестів) . Тоді у вас все ще можуть бути помилкові позитиви, але вам не потрібно нічого попередньо обробляти.

  3. Використовуйте більш досконалі інструменти для "семантичного пошуку" в коді. Я знайшов "coccigrep": http://home.regit.org/software/coccigrep/ Цей вид інструментів дозволяє шукати певні мовні висловлювання (тобто оновлення структури з вказаним іменем), і, безумовно, вони залишають коментарі.


1

Ось певна варіація для всіх решти нас із пізнім позначенням цього питання:

ls -1 src/*.c | xargs -i sh -c "echo;gcc -fpreprocessed -dD -E {} 2>&1 | grep -wi -e one -e two -e three -n | sed 's:^:{}\::'" | cat -s

Список, якщо вихідні файли C

ls -1 src/*.c

переносяться на xargs, який виконує препроцесор у дочірній оболонці

gcc -fpreprocessed -dD -E {} 2>&1

який згодом передається в потрібну команду grep

grep -wi -e one -e two -e three -n

який потім переносять у sed для префіксації кожного рядка з поточним іменем файлу

sed 's:^:{}\::'

Нарешті, всі повторювані порожні рядки згортаються в окремі рядки за допомогою cat:

cat -s

Це працює в системі RHEL6, але я припускаю, що це досить загально для інших * nix систем.

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.