Tâche de traçage (construction d'un graphique de fonction)

 

Supposons que nous ayons du code (fonctions, classes, etc.)

La tâche consiste à créer une pile d'appels. Mais pas seulement de manière linéaire - comme un arbre .

Où le nœud de l'arbre sera l'entrée de la fonction et les branches seront les appels des fonctions suivantes à partir du nœud de fonction actuel.

Par exemple, il existe une telle structure de fonctions :

void Main() {  A(); B(); }

void A() { /*вошли в А*/ a(); b(); c(); }
void B() { /*Вошли в B*/ a(); b(); c(); }

void a() { /*Вошли в а */ }
void b() { /*Вошли в b */ }
void c() { /*Вошли в c */ }

Le résultat ressemblera à ceci


Condition obligatoire :

Vous pouvez ajouter une seule fonction aux fonctions du code existant pour organiser le traçage - juste après "{".
Ne modifiez en aucune façon ni les paramètres d'entrée des fonctions sources, ni leurs résultats, ni le code à l'intérieur.

Cette condition est nécessaire pour ne pas apporter de grandes modifications au code, mais simplement pour insérer une seule et même fonction de traçage (par exemple, appelons-la _TRACE_IN_) dans toutes les fonctions du code existant. Pour obtenir toutes les passes du code source et construire l'arbre d'appel.


Je serais heureux d'entendre toute idée ou variante.
Peu importe comment je le tourne, je tombe sur un cercle vicieux, lorsque je dois appeler non pas une mais deux fonctions pour former un tel arbre. Mais je pourrais n'en avoir besoin que d'un seul. :)

 

Donc, vous voulez faire un programme pour détecter l'algorithme de la source.

J'avais l'habitude de faire quelque chose de similaire pour moi-même lorsque je cassais les programmes des autres en Asm, mais je ne comprends pas votre approche...

pourquoi sous la forme d'un arbre ?

ou peut-être que je ne comprends pas.

 
FLET:

C'est-à-dire que vous voulez faire un programme pour détecter l'algorithme de la source.
J'ai fait quelque chose de similaire pour moi-même quand je cassais les programmes des autres en Asm, mais je ne comprends pas votre approche...
pourquoi en tant qu'arbre ?
ou quelque chose que je ne comprends pas.


Je ne pensais pas à "casser". Mais tu as raison. Il s'agit de construire une structure de code logique.

En d'autres termes, ma tâche est la suivante : lorsque j'active un code de travail (le mien, celui de quelqu'un d'autre ou, par exemple, celui de la livraison standard de MT5), j'obtiens dans une fenêtre séparée la pile complète des fonctions appelées sous forme d'arbre. C'est à dire, à la racine - fonction start() et à partir de là, ça monte et ça descend.....

J'ai mis en place l'arbre il y a longtemps. Il permet d'analyser le temps passé dans les fonctions (pour l'analyse de la qualité du code), le nombre d'appels aux fonctions, le traçage des valeurs des variables, etc. J'ai également mis en œuvre trois options d'affichage de cet arbre - comme ce qui est montré sur la capture d'écran et comme un cercle et un graphique linéaire. Mais j'ai fait tout ça pour des petites choses.

La principale tâche à laquelle j'ai été confronté était de remplir l'arborescence elle-même.

J'ai besoin d'une idée sur la façon d'utiliser une fonction (ou peut-être plusieurs affectations, mais l'essentiel est qu'elles soient alignées), ajoutée à la fonction du code source, pour construire une structure telle que celle de la capture d'écran.

 
sergeev:

J'ai besoin d'une idée pour construire une structure comme celle de l'écranavec une seule fonction, ajoutée au début du code des fonctions.

La preuve de l'impossibilité d'une idée fera l'affaire ?
 
MetaDriver:
La preuve de l'impossibilité d'une idée fera l'affaire ?

will.... Mais seulement après 3 pages de discussion sur les options :))

les implémentations complexes, les variables supplémentaires, l'utilisation de global, ou autre. acceptez tout :)

 
sergeev:

will.... mais seulement après 3 pages de discussion sur les options :))
Lan. En attendant la quatrième page ;-)
 
sergeev:

cela en vaut la peine.... mais seulement après 3 pages de discussion sur les variantes :))


donc la tâche se résumait à remplir le sujet avec 3 pages de texte ? :), ok, faisons-le ;)

1. travailler avec des chaînes de caractères : entrer la fonction, ajouter le nom de la fonction, supprimer la sortie de la fonction, log/trace en permanence sortir la chaîne complète comme une liste linéaire :

start(enter)-func1(enter)-func2(enter)

start(entrée)-func1(entrée)-func2(sortie)

...

cette approche, à mon avis, est une perte de temps.

2. compter manuellement le nombre de fonctions dans le code et ce nombre sera un système de numérotation, c'est-à-dire dans un code de 10 fonctions = base 10, dans un code de 3 fonctions = base 3, en utilisant l'algèbre booléenne, ou peut-être plus facilement en utilisant des matrices, effectuer des opérations d'exclusion ou inclure dans l'entrée/sortie d'une fonction

à peu près, mais encore une fois, imho - est-ce que ça vaut la peine ? il y a beaucoup de travail à faire.

 

IgorM:

La tâche s'est donc réduite à remplir le sujet avec 3 pages de texte ? ), OK, c'est parti ;)

hey, pas si chaud !!! nous comptons chaque page ici :)

1. travailler avec des chaînes de caractères : entrer une fonction, ajouter un nom de fonction, quitter la fonction, la supprimer,

cela ne correspond pas à la condition. Vous n' avez besoin que d'un seul appel - à l'entrée. C'est irréaliste à la sortie. Il peut y avoir plusieurs points de sortie dans une fonction. Mais il n'y a qu'une seule entrée. Par conséquent, l'"ajout" ne doit se faire qu'à l'entrée.
 
sergeev:

hey hey, pas si chaud !!! on a compté toutes les pages ici :)

trop tard, votre souhait a été exprimé par vous ;)

sur le point - je pense que vous devez encore travailler avec des matrices/réseaux multidimensionnels - alors vous aurez un modèle mathématique de votre trace, et comment vous allez gérer les événements d'entrée/sortie de la fonction est une autre question

 
IgorM:

tard, votre souhait a été exprimé par vous ;)

Vous pouvez toujours enterrer une branche. Et ce n'est pas un souhait.

pour le point - je pense que vous devez encore travailler avec des matrices/réseaux multidimensionnels - alors il y aura un modèle mathématique de votre trace, et comment vous allez gérer les événements d'entrée/sortie de la fonction est une autre question

Je ne le comprends pas très bien. Pouvez-vous expliquer sur vos doigts comment les matrices s'intègrent ici ?

L'idée est de mettre les fonctions dans un graphique (un arbre dans le jargon). Mais dans un ordre chronologique clair des appels et de l'identification de ce qui a été appelé. Une seule et même fonction peut être appelée à la fois à partir de start et de init. C'est ce que nous devons réparer.

(Je le développe pour/ sur MQL5, donc j'utilise des classes pour le graphique)

 
sergeev:

graphique (arbre dans le langage courant).

Un arbre est un cas particulier de graphe.