ANSI C na html

Odpowiedz Nowy wątek
2012-10-18 20:26
0

Witam serdecznie.

Dostałem projekt, który przyprawił mnie o ból głowy a mianowicie muszę napisać program w języku C, który przekształci plik zawierający kod źródłowy programu w języku C (zakładamy użycie standardu ANSI C) na plik HTML z kolorowaniem składni i opcjonalnym numerowaniem wierszy. Program powinien umożliwiać kolorowanie grupami kolorów następujących składników kodu źródłowego: słów kluczowych języka C, dyrektyw preprocesora, nazw funkcji bibliotecznych (z bibliotek: stdio, stdlib, string, ctype) oraz użytkownika, nazw zmiennych i stałych oraz typów danych użytkownika. Pozostałe elementy, tzn. łańcuchy znaków, liczby, komentarze itp.

Bardzo proszę o pomoc bo nawet nie mam pojęcia od czego zacząć(jestem początkującym programistą)

Z góry dziękuję.


...

Pozostało 580 znaków

2012-10-18 21:42
1

Skoro C to proponuje zaprzyjaźnić się ze strstr() bo regexpów niestety nie masz.

  1. Numerowanie wierszy jest trywialne
  2. Dyrektywy preprocesora zaczynają się od # a kończą znakiem nowej linii. Więc wszystko co tak wgląda kolorujesz
  3. Słowa kluczowe musisz gdzieś stablicować i znów, szukasz słowa w tekście i kolorujesz
  4. Funkcje biblioteczne jw, funkcje użytkownika musisz najpierw wyszukać, tutaj bez regexpów będzie bieda
  5. Nazwy zmiennych i stałych znów będzie trochę ciężko, bo wyszukać miejsce deklaracji zmiennej jest łatwo, ale potem wyszukać te wystąpienia w kodzie już gorzej bo musisz brać pod uwagę kolejność malowania (np. nazwa zmiennej w stringu nie będzie kolorowana)
  6. Typy danych podobnie, szukasz nazw struktur i klas a potem ich szukasz w programie
  7. Z komentarzami znów będzie problem bez regexpów.

Jesteś pewien że musisz to napisać w czystym C bez żadnych bibliotek?


Masz problem? Pisz na forum, nie do mnie. Nie masz problemów? Kup komputer...

Pozostało 580 znaków

2012-10-18 22:00
Rev
1

@Shalom: parser napisany w ten sposób wymięknie w 9 na 10 przypadkach.

Żeby zrobić to naprawdę porządnie musiałbyś napisać nie parser, a generator parserów bottom-up. Nie jest to zadanie trywialne i raczej nie o to chodzi. Natomiast parser top-down, np. recursive-descent można napisać z palca i jest to zadanie jak najbardziej wykonalne.
Prosty parser tego typu jest nawet na wikipedii: http://en.wikipedia.org/wiki/Recursive_descent_parser
Kilka parserów języka C napisanych w C masz tutaj: http://stackoverflow.com/ques[...]ecursive-descent-parser-for-c


Pozostało 580 znaków

2012-10-19 07:52
1

Jeśli zewnętrzne biblioteki wchodzą w grę, to flex, bison, pcre …

parser napisany w ten sposób wymięknie w 9 na 10 przypadkach.
Kolorowanie nie musi wcale wymagać 100% poprawnego parsera, wystarczy że efekt wizualny będzie ten sam :-)
Co innego gdy piszemy parser celem podpowiadania składni…

edytowany 2x, ostatnio: Azarien, 2012-10-19 07:57
Jak testowałem, to żaden edytor poprawnie przy kolorowaniu nie uwzględniał omijania znaku nowej linii przez . - Zjarek 2012-10-19 19:28
no ale to nie jest wina przyjętej metody, tylko konkretnego niedociągnięcia… - Azarien 2012-10-19 20:11
Może po prostu rzadko widuje się taki kod: http://ideone.com/R2aci - Zjarek 2012-10-19 20:21

Pozostało 580 znaków

2012-10-19 16:04
0

Dziekuję wszystkim za odpowiedzi. PRzemysle temat i w poniedziałek napiszę co i jak.


...

Pozostało 580 znaków

2012-11-03 18:24
0

Oto zalążek


#include <stdio.h>
#include <stdlib.h>
#include <string.h>

char usage[] = "Uzywamy:\n"
               "      c2html [nazwa pliku .C] [nazwa pliku html] [flagi]\n"
               "      Flagi:\n"
               "          -n    Dodawnianie numerowanie wierszy do pliku html.\n";

int main( int numArgs, char *argList[] )
{
  FILE *ifp; /*Plik wejsciowy w jezyku C*/
  FILE *ofp; /*Plik wyjsciowy w html*/
  char c;
  char number = 0; /*Numerowanie linii? 0 = Nie 1 = Tak , domyslnie ustawione na 0 */
  int i = 1; /*Licznik potrzebny do numerowania linii*/

  if( numArgs < 3 )
  {
    fprintf( stderr, "%s\n", usage );
    return 1;
  }

  if( numArgs > 3 && !strcmp( argList[3], "-n" ) )
  {
    number = 1;
  }
  else
  {
    number = 0; /*Przydatne przy nadmiarowosci*/
  }

  if( (ifp = fopen( argList[1], "r" ) ) == NULL )
  {
    fprintf( stderr, "Blad: Nie moge otworzyc %s. Przerywam!\n", argList[1] );
    return 1;
  }

  if( (ofp = fopen( argList[2], "w" ) ) == NULL )
  {
    fprintf( stderr, "Blad: Nie moge zapisac %s. Przerywam!\n", argList[2] );
    return 1;
  }
  /*Naglowki otwierajace dokument html*/
  fprintf( ofp, "<!--Program stworzyli placek1 i placek2\n--!>\n<html>\n<head>\n<title>%s</title>\n</head>\n<body>\n

\n", argList[1] );

/Jezeli wlaczone numerowanie linii, zacznij numerowac linie/
if( number )
{
fprintf( ofp, "%i: ", i );
i++;
}

while( (c = fgetc( ifp ) ) != EOF )
{
/Znaki do zmiany w standardzie HTML ISO-8859-1/
switch( c )
{
case '\"':
fprintf( ofp, """ );
break;
case '\'':
fprintf( ofp, "'" );
break;
case '&':
fprintf( ofp, "&" );
break;
case '<':
fprintf( ofp, "<" );
break;
case '>':
fprintf( ofp, ">" );
break;
case '\n':
{
if( number )
{
fprintf( ofp, "
\n%i: ", i++ ); /Jezeli numerujemy wiersze w tym miejscu
zapamietujemy bierzacy numer!
/
while( ( c = fgetc( ifp ) ) == ' ' )
{
fprintf( ofp, " " ); /Tworzenie spacji za pomoca &nbsp's, w przeciwnym wypadku przegladarka je usunie/
}
ungetc( c, ifp ); /Zwraca ostatni znak zeby czytanie bylo szybsze/
}
else
{
fprintf( ofp, "
\n" );
while( ( c = fgetc( ifp ) ) == ' ' )
{
fprintf( ofp, " " ); /To samo co wyzej tylko w opcji bez numerowania wierszy/
}
ungetc( c, ifp );
}
break;
}
default:
fprintf( ofp, "%c", c );
break;
}
}

/Znaki konczace dokument html/
fprintf( ofp, "

\n</body>\n</html>\n" );

  /*Zamykanie plikow (wejsciowy i wyjsciowy)*/
  fclose( ofp );
  fclose( ifp );

  return 0;
}

I problem Otoż zawartość pliku html jest jakaś dziwna. Są niby te wszystkie heady itd, ale w linijkach pomiedzy wywala mi jakieś dziwne znaki. Ktoś podpowie dlaczego?


...
edytowany 2x, ostatnio: balu, 2012-11-03 18:25

Pozostało 580 znaków

2012-11-03 18:27
0

W załączniku cały kod.


...

Pozostało 580 znaków

2012-11-03 19:37
0

Eh człowieka to czasem ogłupi byle co :D

Przy uruchamianiu na ubuntu dawałem:

./c2html test test1 -n

zamiast

./c2html test.c test1.html -n

i stąd takie dziwne znaczki. Teraz pytanie do was jak się zabrać do tych podpunktów:

Program ma również przeprowadzać uproszczoną kontrolę poprawności
kodu, w skład której wchodzi:
• sprawdzenie kompletności bloków "{...}",
• sprawdzenie kończenia linii średnikiem (zwróć uwagę, że nie każda linia musi się kończyć
średnikiem - uwzględnij wyjątki)


...

Pozostało 580 znaków

2012-11-03 20:40
0

sprawdzenie kompletności bloków "{...}"

Najprościej jest zrobić sobie zmienną pomocniczą i po wykryciu, że np.w tym momencie zaczyna się funkcja, po prostu ją inkrementować gdy napotka {, a dekrementować gdy trafi na }; gdy odnajdziemy deklarację następnej funkcji i zmienna będzie różna od zera lub w którymś momencie będzie mniejsza od zera, gdzieś są źle ustawione nawiasy.
Btw, porozdzielaj ten kod na funkcje...


edytowany 2x, ostatnio: Patryk27, 2012-11-03 20:54

Pozostało 580 znaków

2012-11-03 21:06
0

Pomysł ciekawy, a jak mniej więcej by to wyglądało w implementacji bo nie bardzo wiem jak zacząć?


...

Pozostało 580 znaków

2012-11-03 21:13
0

Najłatwiej, jakbyś miał kod przerobiony na poszczególne tokeny, np.

int main()
{
 for (int i=0; i<10; i++) ;
}

Miałbyś wtedy coś w stylu:

identyfikator -> int
identyfikator -> main
nawias otwierający -> (
nawias zamykający -> )
początek bloku -> {
słowo kluczowe `for` -> for
nawias otwierający -> (
identyfikator -> int
identyfikator -> i
znak równości -> =
liczba -> 0

(i tak dalej)
Potem tylko idziesz po kolei po każdym tokenie i sprawdzasz czy jest on równy początek bloku czy koniec bloku i odpowiednio modyfikujesz zmienną.
Funkcję możesz sprawdzić np.w taki sposób:

1.Pierwszy token to typ*
2.Drugi token to identyfikator określający nazwę funkcji
3.Nawias otwierający
4.Parametry funkcji
5.Nawias zamykający
6.Początek bloku

* - typ to niekoniecznie pojedyncze słowo, np.`void*` to także typ

edytowany 1x, ostatnio: Patryk27, 2012-11-03 22:04

Pozostało 580 znaków

Odpowiedz
Liczba odpowiedzi na stronę

1 użytkowników online, w tym zalogowanych: 0, gości: 1, botów: 0