in reply to nested #if directive matching matching

The range operator is not going to help you much in this case (if you do not want to rely on indentation which I do not suggest). But you can simply count the depth of nesting the if's:
#!/usr/bin/perl use warnings; use strict; my $depth; while (<DATA>) { /#ifdef|#if|#ifndef/ and $depth++; print unless $depth; /#endif/ and $depth--; # this comes after the print not to be prin +ted } __DATA__ { #if 1 #define done 9 #define do 10 #ifdef #define def1 11 #define thread 12 #endif #define mutex 13 #define inter 14 #endif #define intel 15 #define intel_64 16 }

Replies are listed 'Best First'.
Re^2: nested #if directive matching matching
by roboticus (Chancellor) on Jun 26, 2012 at 12:22 UTC

    choroba:

    Actually, you *do* need a stack if you're going to properly handle the #else clauses. Otherwise, you won't remember the previous value(s) of the print vs. don't print states.

    #if 0 this shouldn't print #if 1 nor should this #else nor this #end #else but this should #if 1 as should this #else but not this #end This should print, but where are you storing the information to know it without a stack? #else If you got that one right, howzabout this one? #end

    ...roboticus

    When your only tool is a hammer, all problems look like your thumb.

      That was not part of the spec :-)

        Using the counter, bitshift left and increment if true. Else is an XOR 1. Endif is a bitshift right.

        Initialize with a sentinel value so you know when you're done.

Re^2: nested #if directive matching matching
by tobyink (Canon) on Jun 26, 2012 at 10:12 UTC

    You probably don't want #else to increment $depth.

    perl -E'sub Monkey::do{say$_,for@_,do{($monkey=[caller(0)]->[3])=~s{::}{ }and$monkey}}"Monkey say"->Monkey::do'
      Thanks, removed. I took it from the OP, and it is not present in the test data :-)

      BTW, /#if/ matches both /#ifdef/ and /#ifndef/...