Main Page | Namespace List | Class Hierarchy | Alphabetical List | Class List | File List | Namespace Members | Class Members | File Members | Related Pages

cpp_comment_strip.cpp


SourceForge.net Logo     CTTL on    
    SourceForge    
    Download    
    Latest    
    Documentation    
    Index    
    Library    
    News    
    CVS    
    Repository    
   Other    
   Links    

Demonstrates white space policy based on pre-defined regions of input. The program takes C++ or java program(s) as an input and strips out comments.


File: cpp_comment_strip.cpp

// cpp_comment_strip.cpp

//#define NDEBUG    // define before assert.h to stop assertions from being compiled 
//#define CTTL_TRACE_EVERYTHING //define to turn tracing on
//#define CTTL_TRACE_RULES  //define to turn light tracing on

#include <iostream>
#include "utils/win32_specific.h"
#include "cttl/cttl.h"

#include "utils/fileio.h"
#include "utils/itos.h"
#include "utils/timeutils.h"

#include "utils/pipe_input.h"
#include "example/cpp_comment.h"

using namespace cttl;

int main(int argc, char* argv[])
{
    std::vector< std::string > vect_input_files;

    if ( argc == 2 ) {
        // assume one file was specified as input argument
        vect_input_files.push_back( argv[1] );
    } else
        // assume list of java input files was specified as pipe input
        pipe_input_2_vector( vect_input_files/*, ".java"*/ );

    assert ( vect_input_files.size() );

    input<> inp;
    policy_space< flag_follow_either > void_region;
    typedef const_edge< policy_space< flag_follow_either > > universe_T;
    universe_T universe( new_edge( inp ), void_region );

    for ( size_t file_cnt = 0; file_cnt < vect_input_files.size(); ++file_cnt ) {

        void_region.region_clear();
        file2string( vect_input_files[ file_cnt ], inp.text() );
        assert( inp.length() );

        cpp_comment_lexer< cpp_comment_parser< universe_T > > comment_parser;
        universe.first.go_bof();
        universe.second.go_eof();
        if ( comment_parser.rule_symbols( universe ) ) {
            universe.first.go_bof();
            std::cout << universe.region_difference();
        }
    }

    return 0;
}



File: cpp_comment.h

#ifndef _CTTL_CPP_COMMENT_H_INCLUDED_
#define _CTTL_CPP_COMMENT_H_INCLUDED_

// cpp_comment.h

using namespace cttl;

template< typename UniverseT >
struct comments_base_parser {

    // parser defines two kinds of universes:
    typedef UniverseT universe_T;
    typedef typename UniverseT::strict_edge_T strict_universe_T;
    typedef typename UniverseT::policy_T policy_T;

    policy_T* m_policy_ptr;

    comments_base_parser()
        :
        m_policy_ptr( NULL )
    {
    }

    void policy( policy_T* policy_ptr_ )
    {
        m_policy_ptr = policy_ptr_;
    }

    policy_T* policy()
    {
        assert( m_policy_ptr );
        return m_policy_ptr;
    }

    // default semantic actions:
    size_t cpp_comment( strict_universe_T& )
    {
        return 0;
    }

    size_t c_comment( strict_universe_T& )
    {
        return 0;
    }

    size_t single_quote_interior( strict_universe_T& )
    {
        return 0;
    }

    size_t double_quote_interior( strict_universe_T& )
    {
        return 0;
    }

};

template< typename UniverseT >
struct cpp_comment_parser : public comments_base_parser< UniverseT > {

    typedef UniverseT universe_T;
    typedef typename UniverseT::strict_edge_T strict_universe_T;

    size_t cpp_comment( strict_universe_T& edge_ )
    {
        this->policy()->region_insert( edge_.first.offset(), edge_.second.offset() );
        return 0;
    }

    size_t c_comment( strict_universe_T& edge_ )
    {
        this->policy()->region_insert( edge_.first.offset(), edge_.second.offset() );
        return 0;
    }
};


template< typename UniverseT >
struct cpp_comment_and_literal_parser : public cpp_comment_parser< UniverseT > {

    typedef UniverseT universe_T;
    typedef typename UniverseT::strict_edge_T strict_universe_T;

    size_t single_quote_interior( strict_universe_T& edge_ )
    {
        this->policy()->region_insert( edge_.first.offset(), edge_.second.offset() );
        return 0;
    }

    size_t double_quote_interior( strict_universe_T& edge_ )
    {
        this->policy()->region_insert( edge_.first.offset(), edge_.second.offset() );
        return 0;
    }

};


template< typename ParserT >
struct cpp_comment_lexer : public ParserT {

    // lexer defines two kinds of universes:
    typedef typename ParserT::universe_T universe_T;
    typedef typename universe_T::strict_edge_T strict_universe_T;
    typedef typename universe_T::string_T string_T;

    string_T wack_quote_quote;
    string_T wack_wack;
    string_T wack_asterisk;
    string_T asterisk_wack;

    cpp_comment_lexer()
        :
    wack_quote_quote( "/\"\'" ),
    wack_wack( "//" ),
    wack_asterisk( "/*" ),
    asterisk_wack( "*/" )
    {
    }

    bool rule_symbols( universe_T& edge_ ) {
        
        policy( &edge_.space_policy() );

        return (
            +!!(
                // Find closest character that can begin a comment or a literal.
                // Once found, match the rest of the symbol at the current position
                begin( &wack_quote_quote )
                ^
                (
                    c_single_quote(
                        entity() 
                        &
                        rule( *this, &cpp_comment_lexer< ParserT >::single_quote_interior )
                    )
                    |
                    c_double_quote(
                        entity()
                        &
                        rule( *this, &cpp_comment_lexer< ParserT >::double_quote_interior )
                    )
                    |
                    (   ( &wack_wack + edge_.first( !symbol( '\n' ) | !end() ) )
                        &
                        rule( *this, &cpp_comment_lexer< ParserT >::cpp_comment )
                    )
                    |
                    (   ( &wack_asterisk + !symbol( &asterisk_wack ) )
                        &
                        rule( *this, &cpp_comment_lexer< ParserT >::c_comment )
                    )
                    |
                    // if none of the above matched, this can only be a division operator:
                    '/'
                )
            )

        ).match( edge_ ) != std::string::npos;
    }

};  // struct cpp_comment_lexer

#endif // _CTTL_CPP_COMMENT_H_INCLUDED_



Copyright © 1997-2006 Igor Kholodov mailto:cttl@users.sourceforge.net.

Permission to copy, use, modify, sell and distribute this document is granted provided this copyright notice appears in all copies. This document is provided "as is" without express or implied warranty, and with no claim as to its suitability for any purpose.


Generated on Thu Nov 2 17:44:55 2006 for Common Text Transformation Library by  doxygen 1.3.9.1