| GVPR(1) | General Commands Manual | GVPR(1) |
نام (NAME)
gvpr - زبان پویش و پردازش الگوی گراف
خلاصه دستور (SYNOPSIS)
gvpr [-icnqV?] [ -o outfile ] [ -a args ] [ 'prog' | -f progfile ] [ files ]
توضیحات (DESCRIPTION)
دستور gvpr (که پیشتر با نام gpr شناخته میشد) یک ویرایشگر جریان گراف با الهام از awk است. این ابزار گرافهای ورودی را به خروجی کپی کرده و در صورت نیاز ساختار و ویژگیهای آنها را دگرگون میسازد، گرافهای جدیدی میسازد یا اطلاعات دلخواهی را چاپ میکند. مدل گراف همان مدلی است که توسط libcgraph(3) ارائه شده است. بهویژه، gvpr گرافها را با استفاده از زبان dot میخواند و مینویسد.
بهطور کلی، gvpr هر گراف ورودی را که با $G مشخص میشود پیمایش کرده، تکتک گرهها و یالها را بررسی میکند و آنها را با قواعد گزاره‐عمل (predicate‐action) ارائهشده در برنامهٔ ورودی تطبیق میدهد. قواعد به ترتیب ارزیابی میشوند. به ازای هر گزاره که نتیجهٔ آن «درست» (true) ارزیابی شود، عمل متناظر اجرا میگردد. در طول پیمایش، گره یا یال جاریِ در حال پیمایش با $ نشان داده میشود.
برای هر گراف ورودی، یک زیرگرافِ هدف وجود دارد که با $T مشخص میشود و در ابتدا خالی است و برای جمعآوری موجودیتهای برگزیده استفاده میشود؛ همچنین یک گراف خروجی با نماد $O وجود دارد که برای پردازش نهایی به کار رفته و سپس در خروجی نوشته میشود. بهطور پیشفرض، گراف خروجی همان گراف هدف است. گراف خروجی را میتوان درون برنامه یا، به شکلی محدود، از طریق خط فرمان تنظیم کرد.
گزینهها (OPTIONS)
گزینههای زیر پشتیبانی میشوند:
- -a args
- رشتهٔ args به نشانههای جداشده با فاصله (whitespace) تقسیم میشود و هر یک از این نشانهها به صورت رشتههایی با نامهای ARGV[0],...,ARGV[ARGC-1] در برنامهٔ gvpr در دسترس خواهند بود. نویسههای فاصله در زیررشتههای داخل گیومهٔ تکی یا دوتایی، یا آنهایی که پس از یک بکاسلش قرار دارند، به عنوان جداکننده نادیده گرفته میشوند. بهطور کلی، نویسهٔ بکاسلش هرگونه معنای ویژهٔ نویسهٔ بعدی را غیرفعال میکند. توجه داشته باشید که نشانههای حاصل از چندین پرچم -a به یکدیگر الحاق میشوند.
- -c
- استفاده از گراف مبدأ به عنوان گراف خروجی.
- -i
- استخراج گسترش زیرگراف القاشده با گره (node‐induced subgraph extension) برای گراف خروجی در بستر گراف ریشهٔ آن.
- -o outfile
- باعث میشود جریان خروجی در فایل مشخصشده نوشته شود؛ بهطور پیشفرض، خروجی در stdout نوشته میشود.
- -f progfile
- استفاده از محتویات فایل مشخصشده به عنوان برنامهای که باید روی ورودی اجرا شود. اگر progfile شامل نویسهٔ اسلش باشد، نام به عنوان مسیر فایل در نظر گرفته میشود. در غیر این صورت، gvpr از دایرکتوریهای مشخصشده در متغیر محیطی GVPRPATH برای یافتن فایل استفاده خواهد کرد. اگر -f داده نشود، gvpr از نخستین آرگومان غیرگزینهای به عنوان برنامه استفاده میکند.
- -q
- پیامهای هشدار را خاموش میکند.
- -n
- پیشخوانی گراف (read-ahead) را غیرفعال میکند. بهطور پیشفرض، متغیر $NG روی گراف بعدی که باید پردازش شود تنظیم میشود. این کار نیازمند خواندن گراف بعدی پیش از پردازش گراف جاری است، که اگر گراف بعدی تنها در پاسخ به عملیاتی در حین پردازش گراف جاری تولید شود، ممکن است باعث مسدود شدن (block) فرایند گردد.
- -v
- فعالسازی پیامهای مشروح (verbose).
- -V
- باعث میشود برنامه اطلاعات نسخه را چاپ کرده و خارج شود.
- -?
- باعث میشود برنامه اطلاعات نحوهٔ استفاده را چاپ کرده و خارج شود..SH "عملوندها (OPERANDS)" عملوند زیر پشتیبانی میشود:
- files
- نام فایلهایی شامل ۱ یا چند گراف در زبان dot. اگر هیچ گزینهٔ -f مشخص نشده باشد، نخستین نام از فهرست حذف شده و به عنوان برنامهٔ ورودی استفاده میشود. اگر فهرست فایلها خالی باشد، از stdin استفاده خواهد شد.
برنامهها (PROGRAMS)
یک برنامهٔ gvpr از فهرستی از بندهای گزاره‐کنش تشکیل شده است که یکی از قالبهای زیر را دارند:
- BEGIN { action }
- BEG_G { action }
- N [ predicate ] { action }
- E [ predicate ] { action }
- END_G { action }
- END { action }
یک برنامه میتواند حداکثر شامل یک مورد از هر یک از بندهای BEGIN، END_G و END باشد. میتواند هر تعداد دستور BEG_G، N و E وجود داشته باشد؛ اولی بر روی گرافها اعمال میشود، دومی بر روی گرهها، و سومی بر روی یالها. اینها به بلوکهایی تفکیک میشوند؛ یک بلوک شامل یک دستور اختیاری BEG_G و تمامی دستورهای N و E تا دستور BEG_G بعدی (در صورت وجود) است. معناشناسی سطحبالای یک برنامهٔ gvpr عبارت است از:
ارزیابی بند BEGIN، در صورت وجود.
به ازای هر گراف ورودی G {
به ازای هر بلوک {
تنظیم G به عنوان گراف جاری و شیء جاری.
ارزیابی بند BEG_G، در صورت وجود.
به ازای هر گره و یال در G {
تنظیم گره یا یال به عنوان شیء جاری.
ارزیابی بندهای N یا E، حسب مورد.
}
}
تنظیم G به عنوان شیء جاری.
ارزیابی بند END_G، در صورت وجود.
}
ارزیابی بند END، در صورت وجود.
کنشهای بندهای BEGIN، BEG_G، END_G و END هنگام ارزیابی این بندها اجرا میشوند. برای بندهای N یا E، گزاره یا کنش را میتوان حذف کرد. اگر کنشی بدون گزاره باشد، آن کنش بسته به مورد بر روی هر گره یا یال اجرا میشود. اگر کنشی وجود نداشته باشد و گزاره برابر با درست (true) ارزیابی شود، گره یا یال مربوطه به گراف مقصد اضافه میگردد.
بلوکها به همان ترتیبی که ظاهر میشوند ارزیابی میگردند. درون یک بلوک، بندهای N (و به همین ترتیب، بندهای E) به ترتیبی که ظاهر میشوند ارزیابی میگردند. با این حال توجه داشته باشید که درون یک بلوک، بسته به ترتیب پیمایش، بندهای N یا E ممکن است به صورت درهمتنیده اجرا شوند.
گزارهها و کنشها دنبالهای از دستورها در گویش C هستند که توسط کتابخانهٔ expr(3) پشتیبانی میشود. تنها تفاوت میان گزارهها و کنشها این است که مورد اول باید دارای نوعی باشد که بتوان آن را به عنوان درست یا نادرست تفسیر کرد. در اینجا قواعد معمول C رعایت میشود که در آن مقادیر غیرصفر (non‐zero) درست در نظر گرفته میشوند. این شامل رشتههای غیرخالی و ارجاعهای غیرخالی به گرهها، یالها و غیره میشود. با این حال، اگر بتوان یک رشته را به یک عدد صحیح تبدیل کرد، این مقدار استفاده میشود.
علاوه بر انواع پایهٔ معمول در زبان C (void، int، char، float، long، unsigned و double)، gvpr نوع string را به عنوان مترادفی برای char* و نیز انواع مبتنی بر گراف node_t، edge_t، graph_t و obj_t را فراهم میکند. نوع obj_t میتواند به عنوان یک ابرنوع از ۳ نوع عینی دیگر در نظر گرفته شود؛ نوع پایهٔ صحیح به صورت پویا حفظ میشود. به جز این انواع پایه، تنها عبارتهای نوعِ پشتیبانیشدهٔ دیگر، آرایههای (انجمنی) هستند.
ثابتها از نحو C پیروی میکنند، اما رشتهها میتوانند در "..." یا '...' قرار گیرند. gvpr هم کامنتهای ++C و هم کامنتهای نوع cpp را میپذیرد. برای مورد دوم، اگر خطی با نویسهٔ '#' آغاز شود، بقیهٔ خط نادیده گرفته میشود.
یک دستور میتواند اعلان یک تابع، یک متغیر یا یک آرایه، یا یک دستور اجرایی باشد. برای اعلانها، تنها یک حوزهٔ دید (scope) وجود دارد. اعلانهای آرایه دارای شکل زیر هستند:
type array [ type0 ]
که در آن type0 اختیاری است. اگر مشخص شود، تجزیهکننده (parser) اجبار خواهد کرد که تمام اندیسهای آرایه دارای نوع مشخصشده باشند. اگر مشخص نشود، اشیائی از تمام انواع میتوانند به عنوان اندیس به کار روند. همانند C، متغیرها و آرایهها باید اعلان شوند. به ویژه، یک متغیر اعلاننشده بسته به متن، به عنوان نام یک مشخصه از یک گره، یال یا گراف تفسیر خواهد شد.
دستورهای اجرایی میتوانند یکی از موارد زیر باشند:
| { [ statement ... ] } | |
| expression | // معمولاً var = expression |
| if( expression ) statement [ else statement ] | |
| for( expression ; expression ; expression ) statement | |
| for( array [ var ]) statement | |
| forr( array [ var ]) statement | |
| while( expression ) statement | |
| switch( expression ) case statements | |
| break [ expression ] | |
| continue [ expression ] | |
| return [ expression ] |
در شکل دوم دستور for و دستور forr، متغیر var بر روی هر مقداری که به عنوان نمایه (اندیس) در آرایهٔ مشخصشده استفاده شده تنظیم میشود و سپس statement مرتبط ارزیابی میگردد. برای نمایههای عددی و رشتهای، نمایهها برای for (و به همین ترتیب برای forr) به ترتیب عددی یا الفبایی افزایشی (کاهشی) بازگردانده میشوند. این قابلیت میتواند برای مرتبسازی استفاده شود.
تعریفهای تابع تنها میتوانند در بند BEGIN ظاهر شوند.
عبارتها شامل عبارتهای معمول C هستند. مقایسههای رشتهای با استفاده از == و != عملوند سمت راست را به عنوان یک الگو به منظور تطبیق عبارات باقاعده در نظر میگیرند. الگوها از نحو الگوی تطبیق فایل ksh(1) استفاده میکنند. (برای برابری سادهٔ رشتهها، از تابع strcmp استفاده کنید).
gvpr تلاش خواهد کرد تا در صورت لزوم از یک عبارت به عنوان یک مقدار رشتهای یا عددی استفاده کند. تبدیل نوعهای شبیه به C و قالبهای توابع، در صورت امکان، باعث انجام تبدیلها خواهند شد.
عبارتهای دارای نوع گرافیکی (یعنی graph_t، node_t، edge_t، obj_t) میتوانند با یک ارجاع فیلد به شکل .name همراه باشند. مقدار حاصل، مقدار مشخصهای به نام name از شیء دادهشده است. علاوه بر این، در زمینههای خاصی یک شناسهٔ اعلاننشده و تغییرنیافته به عنوان نام یک مشخصه در نظر گرفته میشود. به ویژه، چنین شناسههایی به ترتیب نشاندهندهٔ مشخصههای گره یا یال جاری در بندهای N و E، و گراف جاری در بندهای BEG_G و END_G هستند.
طبق روال معمول در مدل libcgraph(3)، مشخصهها دارای مقدار رشتهای هستند. علاوه بر این، gvpr از برخی شبهمشخصههای اشیاء گراف پشتیبانی میکند که لزوماً دارای مقدار رشتهای نیستند. اینها خصوصیات ذاتی اشیاء گراف را بازتاب میدهند و توسط کاربر قابل تنظیم نیستند.
- head : node_t
- سر یک یال..TP tail : node_t دمِ یک یال.
- name : string
- نام یک یال، گره یا گراف. نام یک یال به فرم "<tail‐name><edge‐op><head‐name>[<key>]" است، که در آن <edge‐op> بسته به جهتدار بودن یا نبودن گراف، برابر با "->" یا "--" است. بخش درون قلاب [<key>] تنها زمانی ظاهر میشود که یال دارای کلیدی غیربدیهی (غیرساده) باشد.
- indegree : int
- درجهٔ ورودی یک گره.
- outdegree : int
- درجهٔ خروجی یک گره.
- degree : int
- درجهٔ یک گره.
- X : double
- مختصات X یک گره. (فرض میکند که گره دارای مشخصهٔ pos است.)
- Y : double
- مختصات Y یک گره. (فرض میکند که گره دارای مشخصهٔ pos است.)
- root : graph_t
- گراف ریشهٔ یک شیء. ریشهٔ یک گراف ریشه، خودش است.
- parent : graph_t
- گراف والد یک زیرگراف. والد یک گراف ریشه برابر با NULL است.
- n_edges : int
- تعداد یالهای موجود در گراف.
- n_nodes : int
- تعداد گرههای موجود در گراف.
- directed : int
- در صورتی که گراف جهتدار باشد، مقدار درست (غیرصفر) است.
- strict : int
- در صورتی که گراف اکید (strict) باشد، مقدار درست (غیرصفر) است.
توابع توکار (BUILT‐IN FUNCTIONS)
توابع زیر بهصورت توکار در gvpr تعریف شدهاند. توابعی که ارجاعاتی به اشیاء گراف بازمیگردانند، در صورت بروز خطا NULL برمیگردانند.
گرافها و زیرگراف (Graphs and subgraph)
- graph(s : string, t : string) : graph_t
- گرافی با نام s و از نوع مشخصشده توسط رشتهٔ t ایجاد میکند. بدون در نظر گرفتن بزرگی و کوچکی حروف، نویسههای U, D, S, N به ترتیب بیانگر بدونجهت (undirected)، جهتدار (directed)، اکید (strict) و غیراکید (non‐strict) هستند. اگر t خالی باشد، یک گراف جهتدار و غیراکید ایجاد میشود.
- subg(g : graph_t, s : string) : graph_t
- زیرگرافی با نام s در گراف g ایجاد میکند. اگر این زیرگراف از قبل وجود داشته باشد، همان بازگردانده میشود.
- isSubg(g : graph_t, s : string) : graph_t
- زیرگراف با نام s در گراف g را در صورت وجود بازمیگرداند، وگرنه NULL برمیگرداند.
- fstsubg(g : graph_t) : graph_t
- اولین زیرگراف موجود در گراف g را بازمیگرداند، یا در صورت نبود، NULL برمیگرداند.
- nxtsubg(sg : graph_t) : graph_t
- زیرگراف بعدی پس از sg را برمیگرداند، یا NULL بازمیگرداند.
- isDirect(g : graph_t) : int
- اگر و تنها اگر g جهتدار باشد، مقدار درست (true) بازمیگرداند.
- isStrict(g : graph_t) : int
- اگر و تنها اگر g اکید باشد، مقدار درست (true) بازمیگرداند.
- nNodes(g : graph_t) : int
- تعداد گرههای موجود در g را برمیگرداند.
- nEdges(g : graph_t) : int
- تعداد یالهای موجود در g را برمیگرداند..SS "گرهها (Nodes)"
- node(g : graph_t, s : string) : node_t
- گرهای با نام s در گراف g ایجاد میکند. اگر چنین گرهای از قبل وجود داشته باشد، همان بازگردانده میشود.
- subnode(sg : graph_t, n : node_t) : node_t
- گره n را در زیرگراف sg درج میکند. گره را بازمیگرداند.
- fstnode(g : graph_t) : node_t
- نخستین گره در گراف g، یا در صورت عدم وجود، NULL را بازمیگرداند.
- nxtnode(n : node_t) : node_t
- گره بعدی پس از n در گراف ریشه، یا NULL را بازمیگرداند.
- nxtnode_sg(sg : graph_t, n : node_t) : node_t
- گره بعدی پس از n در sg، یا NULL را بازمیگرداند.
- isNode(sg : graph_t, s : string) : node_t
- در (زیر)گراف sg به دنبال گرهای با نام s میگردد. اگر چنین گرهای وجود داشته باشد، بازگردانده میشود؛ در غیر این صورت، NULL بازگردانده میشود.
- isSubnode(sg : graph_t, n : node_t) : int
- اگر گره n در (زیر)گراف sg باشد مقداری غیرصفر، و در غیر این صورت صفر بازمیگرداند.
- indegreeOf(sg : graph_t, n : node_t) : int
- درجه ورودی گره n در (زیر)گراف sg را بازمیگرداند.
- outdegreeOf(sg : graph_t, n : node_t) : int
- درجه خروجی گره n در (زیر)گراف sg را بازمیگرداند.
- degreeOf(sg : graph_t, n : node_t) : int
- درجه گره n در (زیر)گراف sg را بازمیگرداند.
- rename(n : node_t, newname : string) : int
- نام n را به newname تغییر میدهد و در صورت موفقیت 0، یا در صورت وجود گرهای دیگر با همین نام -1 بازمیگرداند.
یالها (Edges)
- edge(t : node_t, h : node_t, s : string) : edge_t
- یالی با گره مبدأ t، گره مقصد h و نام s در گراف ریشه ایجاد میکند. اگر گراف بدونجهت باشد، تمایز میان گرههای مبدأ و مقصد بیاهمیت است. اگر چنین یالی از قبل وجود داشته باشد، همان بازگردانده میشود.
- edge_sg(sg : graph_t, t : node_t, h : node_t, s : string) : edge_t
- یالی با گره مبدأ t، گره مقصد h و نام s در (زیر)گراف sg (و تمام گرافهای والد) ایجاد میکند. اگر گراف بدونجهت باشد، تمایز میان گرههای مبدأ و مقصد بیاهمیت است. اگر چنین یالی از قبل وجود داشته باشد، همان بازگردانده میشود.
- subedge(g : graph_t, e : edge_t) : edge_t
- یال e را در زیرگراف g درج میکند. یال را بازمیگرداند.
- isEdge(t : node_t, h : node_t, s : string) : edge_t
- به دنبال یالی با گره مبدأ t، گره مقصد h و نام s میگردد. اگر گراف بدونجهت باشد، تمایز میان گرههای مبدأ و مقصد بیاهمیت است. اگر چنین یالی وجود داشته باشد بازگردانده میشود؛ در غیر این صورت، NULL بازگردانده میشود.
- isEdge_sg(sg : graph_t, t : node_t, h : node_t, s : string) : edge_t
- در (زیر)گراف sg به دنبال یالی با گره مبدأ t، گره مقصد h و نام s میگردد. اگر گراف بدونجهت باشد، تمایز میان گرههای مبدأ و مقصد بیاهمیت است. اگر چنین یالی وجود داشته باشد بازگردانده میشود؛ در غیر این صورت، NULL بازگردانده میشود.
- isSubedge(sg : graph_t, e : edge_t) : int
- اگر یال e در (زیر)گراف sg باشد مقداری غیرصفر، و در غیر این صورت صفر بازمیگرداند.
- fstout(n : node_t) : edge_t
- نخستین یال خروجی گره n را در گراف ریشه بازمیگرداند.
- fstout_sg(sg : graph_t, n : node_t) : edge_t
- نخستین یال خروجی گره n را در (زیر)گراف sg بازمیگرداند.
- nxtout(e : edge_t) : edge_t
- یال خروجی بعدی پس از e را در گراف ریشه بازمیگرداند.
- nxtout_sg(sg : graph_t, e : edge_t) : edge_t
- یال خروجی بعدی پس از e را در گراف sg بازمیگرداند.
- fstin(n : node_t) : edge_t
- نخستین یال ورودی گره n را در گراف ریشه بازمیگرداند.
- fstin_sg(sg : graph_t, n : node_t) : edge_t
- نخستین یال ورودی گره n را در گراف sg بازمیگرداند.
- nxtin(e : edge_t) : edge_t
- یال ورودی بعدی پس از e را در گراف ریشه بازمیگرداند.
- nxtin_sg(sg : graph_t, e : edge_t) : edge_t
- یال ورودی بعدی پس از e را در گراف sg بازمیگرداند.
- fstedge(n : node_t) : edge_t
- نخستین یال گره n را در گراف ریشه بازمیگرداند.
- fstedge_sg(sg : graph_t, n : node_t) : edge_t
- نخستین یال گره n را در گراف sg بازمیگرداند.
- nxtedge(e : edge_t, n : node_t) : edge_t
- یال بعدی پس از e را در گراف ریشه بازمیگرداند.
- nxtedge_sg(sg : graph_t, e : edge_t, n : node_t) : edge_t
- یال بعدی پس از e را در گراف sg بازمیگرداند.
- opp(e : edge_t, n : node_t) : node_t
- گره دیگر روی یال e که برابر با n نیست را بازمیگرداند. اگر n گرهای از e نباشد، NULL بازگردانده میشود. این تابع هنگام استفاده از fstedge و nxtedge برای برشمردن همسایگان n میتواند مفید باشد..SS "ورودی/خروجی گراف (Graph I/O)"
- write(g : graph_t) : void
- گراف g را با قالب dot در جریان خروجی چاپ میکند.
- writeG(g : graph_t, fname : string) : void
- گراف g را با قالب dot درون فایل fname چاپ میکند.
- fwriteG(g : graph_t, fd : int) : void
- گراف g را با قالب dot در جریان باز مشخصشده با عدد صحیح fd چاپ میکند.
- readG(fname : string) : graph_t
- گراف خواندهشده از فایل fname را برمیگرداند. گراف باید در قالب dot باشد. اگر هیچ گرافی قابل خواندن نباشد، NULL برگردانده میشود.
- freadG(fd : int) : graph_t
- گراف بعدی خواندهشده از جریان باز fd را برمیگرداند. در انتهای فایل NULL برمیگرداند.
متفرقههای گراف (Graph miscellany)
- delete(g : graph_t, x : obj_t) : void
- شیء x را از گراف g حذف میکند. اگر g برابر NULL باشد، تابع از گراف ریشهٔ x استفاده میکند. اگر x یک گراف یا زیرگراف باشد، بسته میشود مگر اینکه x قفل باشد.
- isIn(g : graph_t, x : obj_t) : int
- اگر x در زیرگراف g باشد، مقدار درست (true) را برمیگرداند.
- cloneG(g : graph_t, s : string) : graph_t
- یک کلون (نسخهٔ مشابه) از گراف g با نام s ایجاد میکند. اگر s برابر "" باشد، گراف ایجادشده نامی یکسان با g خواهد داشت.
- clone(g : graph_t, x : obj_t) : obj_t
- یک کلون از شیء x در گراف g ایجاد میکند. بهویژه، شیء جدید دارای مشخصههای نام/مقدار و ساختاری مشابه با شیء اصلی خواهد بود. اگر شیئی با همان کلیدِ x از پیش موجود باشد، مشخصههای آن با مشخصههای x بازنویسی شده و شیء برگردانده میشود. اگر یک یال کلون شود، هر دو نقطهٔ انتهایی آن نیز بهطور ضمنی کلون میشوند. اگر یک گراف کلون شود، تمام گرهها، یالها و زیرگرافهای آن بهطور ضمنی کلون میشوند. اگر x یک گراف باشد، g میتواند NULL باشد که در این حالت شیء کلونشده یک گراف ریشهٔ جدید خواهد بود. در این وضعیت، فراخوانی معادل cloneG(x,"") است.
- copy(g : graph_t, x : obj_t) : obj_t
- یک کپی از شیء x در گراف g ایجاد میکند، بهطوری که شیء جدید دارای مشخصههای نام/مقدار مشابه با شیء اصلی است. اگر شیئی با همان کلیدِ x از پیش موجود باشد، مشخصههای آن با مشخصههای x بازنویسی شده و شیء برگردانده میشود. توجه داشته باشید که این یک کپی سطحی (shallow copy) است. اگر x یک گراف باشد، هیچیک از گرهها، یالها یا زیرگرافهای آن به گراف جدید کپی نمیشوند. اگر x یک یال باشد، در صورت لزوم نقاط انتهایی ایجاد میشوند، اما کلون نمیشوند. اگر x یک گراف باشد، g میتواند NULL باشد که در این حالت شیء کپیشده یک گراف ریشهٔ جدید خواهد بود.
- copyA(src : obj_t, tgt : obj_t) : int
- مشخصههای شیء src را در شیء tgt کپی میکند و هرگونه مقدار مشخصهای را که tgt در ابتدا داشته بازنویسی میکند.
- induce(g : graph_t) : void
- گراف g را به زیرگراف القاشده با گرههایش (node‐induced) در گراف ریشهاش گسترش میدهد.
- hasAttr(src : obj_t, name : string) : int
- اگر شیء src دارای مشخصهای با نام name باشد، مقداری غیرصفر برمیگرداند؛ در غیر این صورت 0 برمیگرداند.
- isAttr(g : graph_t, kind : string, name : string) : int
- اگر مشخصهٔ name در g برای اشیائی از نوع kind دادهشده تعریف شده باشد، مقداری غیرصفر برمیگرداند. برای گرهها، یالها و گرافها، kind باید بهترتیب "N"، "E" و "G" باشد. در غیر این صورت 0 برمیگرداند.
- aget(src : obj_t, name : string) : string
- مقدار مشخصهٔ name را در شیء src برمیگرداند. این تابع برای مواردی مفید است که name با یکی از کلیدواژهها مانند "head" یا "root" تداخل دارد. اگر مشخصه در گراف اعلان نشده باشد، تابع آن را با مقدار پیشفرض "" مقداردهی اولیه میکند. برای جلوگیری از این رفتار، باید از توابع hasAttr یا isAttr جهت بررسی وجود مشخصه استفاده شود.
- aset(src : obj_t, name : string, value : string) : int
- مقدار مشخصهٔ name را در شیء src به value تنظیم میکند. در صورت موفقیت 0 و در صورت شکست مقداری غیرصفر (non‐zero) برمیگرداند. توضیحات aget در بالا را ببینید.
- getDflt(g : graph_t, kind : string, name : string) : string
- مقدار پیشفرض مشخصهٔ name را در اشیاء از نوع kind در g برمیگرداند. برای گرهها، یالها و گرافها، kind باید بهترتیب "N"، "E" و "G" باشد. اگر مشخصه در گراف اعلان نشده باشد، تابع آن را با مقدار پیشفرض "" مقداردهی اولیه میکند. برای جلوگیری از این رفتار، باید از تابع isAttr برای بررسی وجود مشخصه استفاده شود.
- setDflt(g : graph_t, kind : string, name : string, value : string) : int
- مقدار پیشفرض مشخصهٔ name را در اشیاء از نوع kind دادهشده در g برابر value تنظیم میکند. برای گرهها، یالها و گرافها، kind باید بهترتیب "N"، "E" و "G" باشد. در صورت موفقیت 0 و در صورت شکست مقداری غیرصفر برمیگرداند. توضیحات getDflt در بالا را ببینید.
- fstAttr(g : graph_t, kind : string) : string
- نام اولین مشخصه از اشیاء موجود در g از نوع kind دادهشده را برمیگرداند. برای گرهها، یالها و گرافها، kind باید بهترتیب "N"، "E" و "G" باشد. اگر هیچ مشخصهای وجود نداشته باشد، رشتهٔ "" برگردانده میشود.
- nxtAttr(g : graph_t, kind : string, name : string) : string
- نام مشخصهٔ بعدی از اشیاء موجود در g از نوع kind دادهشده را پس از مشخصهٔ name برمیگرداند. آرگومان name باید نام یک مشخصهٔ موجود باشد؛ این مقدار معمولاً حاصل بازگشتی از فراخوانی پیشین به fstAttr یا nxtAttr خواهد بود. برای گرهها، یالها و گرافها، kind باید بهترتیب "N"، "E" و "G" باشد. اگر مشخصهٔ دیگری باقی نمانده باشد، رشتهٔ "" برگردانده میشود.
- compOf(g : graph_t, n : node_t) : graph_t
- مؤلفهٔ همبند از گراف g شامل گره n را بهصورت زیرگرافی از g برمیگرداند. این زیرگراف فقط شامل گرهها است. برای افزودن یالها میتوان از induce استفاده کرد. اگر n در g وجود نداشته باشد، تابع با شکست مواجه شده و NULL برمیگرداند. همبندی بر پایهٔ گراف بدون جهتِ زیربنایی g تعیین میشود.
- kindOf(obj : obj_t) : string
- نوع شیء obj را برمیگرداند. برای گرهها، یالها و گرافها بهترتیب "N"، "E" و "G" برمیگرداند.
- lock(g : graph_t, v : int) : int
- قفلگذاری گراف را روی گرافهای ریشه پیادهسازی میکند. اگر عدد صحیح v مثبت باشد، گراف طوری تنظیم میشود که فراخوانیهای بعدی به delete اثر فوری نداشته باشند. اگر v صفر باشد، قفل گراف باز میشود. اگر در زمانی که گراف قفل بوده فراخوانی برای حذف آن انجام شده باشد، گراف بسته میشود. اگر v منفی باشد، هیچ عملی انجام نمیشود. در تمام موارد، مقدار قفل قبلی بازگردانده میشود..SS "رشتهها (Strings)"
- sprintf(fmt : string, ...) : string
- رشته حاصل از قالببندی مقادیر عبارتهای پس از fmt را بر اساس قالب printf(3) در fmt برمیگرداند.
- gsub(str : string, pat : string) : string
- gsub(str : string, pat : string, repl : string) : string
- رشته str را در حالی که تمام زیررشتههای منطبق با pat بهترتیب حذف یا با repl جایگزین شدهاند، برمیگرداند.
- sub(str : string, pat : string) : string
- sub(str : string, pat : string, repl : string) : string
- رشته str را در حالی که چپترین زیررشتهٔ منطبق با pat بهترتیب حذف یا با repl جایگزین شده است، برمیگرداند. نویسههای '^' و '$' میتوانند بهترتیب در ابتدا و انتهای pat برای مقید کردن الگو به ابتدا یا انتهای str به کار روند.
- substr(str : string, idx : int) : string
- substr(str : string, idx : int, len : int) : string
- زیررشتهای از str را که از موقعیت idx شروع میشود، بهترتیب تا انتهای رشته یا به طول len، برمیگرداند. نمایهگذاری از 0 آغاز میشود. اگر idx منفی باشد یا idx بزرگتر از طول str باشد، یک خطای مهلک رخ میدهد. بهطور مشابه، در حالت دوم، اگر len منفی باشد یا idx + len بزرگتر از طول str باشد، یک خطای مهلک رخ میدهد.
- strcmp(s1 : string, s2 : string) : int
- تابع استاندارد C به نام strcmp(3) را ارائه میدهد.
- length(s : string) : int
- طول رشته s را برمیگرداند.
- index(s : string, t : string) : int
- rindex(s : string, t : string) : int
- نمایهٔ نویسهای در رشته s را که در آن چپترین (راستترین) نسخه از رشته t یافت میشود، یا در صورتی که t زیررشتهای از s نباشد، -1 را برمیگرداند.
- match(s : string, p : string) : int
- نمایهٔ نویسهای در رشته s را که در آن چپترین تطابق الگوی p یافت میشود، یا اگر هیچ زیررشتهای از s با p مطابقت نداشته باشد، -1 را برمیگرداند.
- toupper(s : string) : string
- نسخهای از s را با نویسههای الفبایی تبدیلشده به حروف بزرگ برمیگرداند.
- tolower(s : string) : string
- نسخهای از s را با نویسههای الفبایی تبدیلشده به حروف کوچک برمیگرداند.
- canon(s : string) : string
- نسخهای از s را که مناسب استفاده به عنوان یک شناسه در یک فایل dot است، برمیگرداند.
- html(g : graph_t, s : string) : string
- نسخهای “جادویی” از s را به عنوان یک رشته HTML برمیگرداند. این تابع معمولاً برای پیوست کردن یک برچسب شبهHTML به یک شیء گراف استفاده میشود. توجه داشته باشید که رشتهٔ بازگشتی درون g قرار دارد. بهویژه، هنگامی که g بسته شود، این رشته آزاد خواهد شد، و برای اینکه مانند یک رشته HTML عمل کند، باید با شیئی از g به کار رود. علاوه بر این، توجه داشته باشید که علامتهای زاویهدار (angle bracket quotes) نباید بخشی از s باشند. این علامتها در صورتی که g در قالب مشخص DOT نوشته شود، اضافه خواهند شد.
- ishtml(s : string) : int
- اگر و تنها اگر s یک رشته HTML باشد، مقداری غیرصفر برمیگرداند.
- xOf(s : string) : string
- اگر s به شکل "x,y" باشد، که در آن هر دو x و y عددی هستند، رشته "x" را برمیگرداند.
- yOf(s : string) : string
- اگر s به شکل "x,y" باشد، که در آن هر دو x و y عددی هستند، رشته "y" را برمیگرداند.
- llOf(s : string) : string
- اگر s به شکل "llx,lly,urx,ury" باشد، که در آن همگی llx، lly، urx و ury عددی هستند، رشته "llx,lly" را برمیگرداند.
- urOf(s)
- urOf(s : string) : string اگر s به شکل "llx,lly,urx,ury" باشد، که در آن همگی llx، lly، urx و ury عددی هستند، رشته "urx,ury" را برمیگرداند.
- sscanf(s : string, fmt : string, ...) : int
- رشته s را بررسی کرده و مقادیر را مطابق با قالب sscanf(3) در fmt استخراج میکند. مقادیر در نشانیهای پس از fmt ذخیره میشوند؛ نشانیهایی به فرم &v که در آن v متغیری تعریفشده از نوع صحیح است. تعداد مواردی که با موفقیت پیمایش شدهاند را برمیگرداند.
- split(s : string, arr : array, seps : string) : int
- split(s : string, arr : array) : int
- tokens(s : string, arr : array, seps : string) : int
- tokens(s : string, arr : array) : int
- تابع split
رشته s را
به فیلدها
تقسیم
میکند، در
حالی که
تابع tokens
رشته را به
نشانهها (tokens)
تجزیه
مینماید.
یک فیلد
شامل تمام
نویسههای
غیرجداکننده
بین دو
نویسهٔ
جداکننده
یا ابتدا یا
انتهای
رشته است.
بنابراین،
یک فیلد
ممکن است یک
رشته خالی
باشد. یک
نشانه (token)،
زیررشتهای
حداکثری و
غیرخالی
است که
نویسهٔ
جداکنندهای
دربرندارد.
نویسههای
جداکننده
همانهایی
هستند که در
آرگومان seps
مشخص
شدهاند.
اگر seps
ارائه
نشود،
مقدار
پیشفرض " \t\n"
خواهد بود.
این توابع
تعداد
فیلدها یا
نشانهها
را
برمیگردانند.
فیلدها و نشانهها در آرایهٔ آرگومان ذخیره میشوند. آرایه باید دارای مقادیری از نوع string بوده و دارای نوع نمایهٔ int باشد. مدخلها با اعداد صحیح متوالی، با شروع از 0 نمایهگذاری میشوند. هر مقداری که از قبل در آرایه ذخیره شده باشد، پس از بازگشت تابع یا رونویسی خواهد شد، یا همچنان در آن باقی خواهد ماند..SS "ورودی/خروجی (I/O)"
- print(...) : void
- print( expr, ... ) نمایش رشتهایِ هر یک از آرگومانها را به نوبت روی stdout چاپ کرده و در ادامه یک نویسهٔ خطجدید میگذارد.
- printf(fmt : string, ...) : int
- printf(fd : int, fmt : string, ...) : int
- رشتهٔ حاصل از قالببندی مقادیر عبارتهای پس از fmt را بر اساس قالب fmt تابع printf(3) چاپ میکند. در صورت موفقیت 0 را برمیگرداند. بهطور پیشفرض، روی stdout چاپ میکند. اگر عدد صحیح اختیاری fd مشخص شده باشد، خروجی در جریانِ باز مرتبط با fd نوشته میشود.
- scanf(fmt : string, ...) : int
- scanf(fd : int, fmt : string, ...) : int
- مقادیر را از یک جریان ورودی مطابق با قالب fmt تابع scanf(3) میپویشد. مقادیر در آدرسهای پس از fmt ذخیره میشوند؛ آدرسهایی با ساختار &v که در آن v متغیری اعلانشده از نوع صحیح است. بهطور پیشفرض، از stdin میخواند. اگر عدد صحیح اختیاری fd مشخص شده باشد، ورودی از جریان بازِ مرتبط با fd خوانده میشود. تعداد مواردی که با موفقیت پویش شدهاند را برمیگرداند.
- openF(s : string, t : string) : int
- فایل s را
به عنوان یک
جریان I/O باز
میکند.
آرگومان
رشتهای t
نحوهٔ باز
شدن فایل را
مشخص
میکند.
آرگومانها
مشابه
آرگومانهای
تابع C با
نام fopen(3)
هستند. این
تابع یک عدد
صحیح به
عنوان
نشاندهندهٔ
جریان، یا
در صورت
بروز خطا -1
برمیگرداند.
طبق معمول، جریانهای 0، 1 و 2 از قبل به ترتیب به عنوان stdin، stdout و stderr باز هستند. از آنجا که gvpr ممکن است از stdin برای خواندن گرافهای ورودی استفاده کند، کاربر باید از استفاده از این جریان خودداری کند.
- closeF(fd : int) : int
- جریانِ باز مشخصشده توسط عدد صحیح fd را میبندد. جریانهای 0، 1 و 2 را نمیتوان بست. در صورت موفقیت 0 برمیگرداند.
- readL(fd : int) : string
- خط بعدی خواندهشده از جریان ورودی fd را برمیگرداند. در انتهای فایل، رشتهٔ خالی "" را برمیگرداند. توجه داشته باشید که نویسهٔ خطجدید در رشتهٔ بازگرداندهشده باقی میماند.
ریاضیات (Math)
- exp(d : double) : double
- مقدار e به توان d را برمیگرداند.
- log(d : double) : double
- لگاریتم طبیعی d را برمیگرداند.
- sqrt(d : double) : double
- جذر عدد اعشاری مضاعف d را برمیگرداند.
- pow(d : double, x : double) : double
- مقدار d به توان x را برمیگرداند.
- cos(d : double) : double
- کسینوس d را برمیگرداند.
- sin(d : double) : double
- سینوس d را برمیگرداند.
- atan2(y : double, x : double) : double
- آرکتانژانت y/x را در بازهٔ -pi تا pi برمیگرداند.
- MIN(y : double, x : double) : double
- کمینهٔ y و x را برمیگرداند.
- MAX(y : double, x : double) : double
- بیشینهٔ y و x را برمیگرداند..SS "آرایههای انجمنی (Associative Arrays)"
- # arr : int
- تعداد عناصر موجود در آرایه arr را برمیگرداند.
- idx in arr : int
- اگر مقداری برای نمایه idx در آرایه arr تنظیم شده باشد، مقدار 1 را برمیگرداند. در غیر این صورت 0 را برمیگرداند.
- unset(v : array, idx) : int
- عنصر با نمایه idx را حذف میکند. اگر عنصر وجود داشت، 1 و در غیر این صورت 0 را برمیگرداند.
- unset(v : array) : void
- آرایه را بازنشانی و مجدداً مقداردهی اولیه میکند.
متفرقه (Miscellaneous)
- exit(v : int) : void
- باعث خروج gvpr با کد خروج v میشود.
- system(cmd : string) : int
- تابع استاندارد زبان سی system(3) را فراهم میکند. این تابع cmd را در محیط شل کاربر اجرا کرده و وضعیت خروج شل را برمیگرداند.
- rand() : double
- یک مقدار double شبه‐تصادفی بین 0 و 1 را برمیگرداند.
- srand() : int
- srand(v : int) : int
- یک بذر (seed) برای مولد اعداد تصادفی تعیین میکند. آرگومان اختیاری بذر را مشخص میکند؛ اگر حذف شود، زمان فعلی استفاده میشود. مقدار بذر قبلی برگردانده میشود. srand باید قبل از هر فراخوانی به rand اجرا شود.
- colorx(color : string, fmt : string) : string
- یک رنگ را از قالبی به قالب دیگر تبدیل میکند. آرگومان color باید یک رنگ در یکی از قالبهای متنی شناختهشده باشد. مقدار fmt باید یکی از مقادیر "RGB"، "RGBA"، "HSV" یا "HSVA" باشد. در صورت بروز خطا، یک رشته خالی برگردانده میشود.
متغیرهای توکار (BUILT‐IN VARIABLES)
gvpr متغیرهای توکار خاصی فراهم میکند که مقادیر آنها بسته به زمینه (context) بهطور خودکار توسط gvpr تنظیم میشود. بهجز در موارد ذکر شده، کاربر نمیتواند مقادیر آنها را تغییر دهد.
- $ : obj_t
- بسته به زمینه، نشاندهنده شیء فعلی (گره، یال، گراف) است. این متغیر در بندهای BEGIN یا END در دسترس نیست.
- $F : string
- نام فایل ورودی فعلی است.
- $G : graph_t
- نشاندهنده گراف فعلی در حال پردازش است. در بندهای BEGIN یا END در دسترس نیست.
- $NG : graph_t
- نشاندهنده گراف بعدی برای پردازش است. اگر $NG برابر با NULL باشد، گراف فعلی $G آخرین گراف است. توجه داشته باشید که اگر ورودی از stdin دریافت شود، آخرین گراف تا زمانی که لوله (pipe) ورودی بسته نشود قابل تشخیص نیست. این متغیر در بندهای BEGIN یا END، یا در صورت استفاده از گزینه -n در دسترس نیست.
- $O : graph_t
- نشاندهنده گراف خروجی است. پیش از پیمایش گراف، با گراف هدف مقداردهی اولیه میشود. پس از پیمایش و هرگونه عملیات END_G، اگر به یک گراف غیر‐خالی اشاره کند، آن گراف در جریان خروجی چاپ میشود. این متغیر فقط در بندهای N، E و END_G معتبر است. گراف خروجی میتواند توسط کاربر تنظیم شود.
- $T : graph_t
- نشاندهنده گراف هدف فعلی است. این یک زیرگراف از $G است و تنها در بندهای N، E و END_G در دسترس است.
- $tgtname : string
- نشاندهنده نام گراف هدف است. بهطور پیشفرض روی "gvpr_result" تنظیم شده است. اگر چندین بار در طول اجرای gvpr استفاده شود، یک عدد صحیح به انتهای نام افزوده خواهد شد. این متغیر میتواند توسط کاربر تنظیم شود.
- $tvroot : node_t
- گره آغازین را برای پیمایش اولعمق یا اولسطح (جهتدار یا بدونجهت) از گراف مشخص میکند (مقایسه کنید با $tvtype در زیر). مقدار پیشفرض برای هر گراف ورودی NULL است. پس از پیمایش در ریشه مشخصشده، اگر مقدار $tvroot تغییر کرده باشد، پیمایش جدیدی با مقدار جدید $tvroot آغاز خواهد شد. همچنین به $tvnext در زیر مراجعه کنید.
- $tvnext : node_t
- گره آغازین بعدی را برای پیمایش اولعمق یا اولسطح (جهتدار یا بدونجهت) از گراف مشخص میکند (مقایسه کنید با $tvtype در زیر). اگر پیمایشی به پایان برسد و $tvroot بازنشانی نشده باشد، اما $tvnext مقداردهی شده ولی استفاده نشده باشد، این گره بهعنوان انتخاب بعدی برای $tvroot استفاده خواهد شد. مقدار پیشفرض برای هر گراف ورودی NULL است.
- $tvedge : edge_t
- برای پیمایشهای BFS و DFS، روی یالی تنظیم میشود که برای رسیدن به گره یا یال فعلی پیموده شده است. در ابتدای پیمایش، یا برای سایر انواع پیمایش، مقدار آن NULL است.
- $tvtype : tvtype_t
- نحوه پیمایش گراف توسط gvpr را مشخص میکند. این متغیر تنها میتواند یکی از مقادیر ثابت با پیشوند "TV_" که در زیر شرح داده شده است را بپذیرد. TV_flat مقدار پیشفرض است.
- در کتابخانه گراف زیربنایی cgraph(3)، به یالها در گرافهای بدونجهت یک جهت دلخواه اختصاص داده میشود. این ویژگی برای پیمایشهایی نظیر TV_fwd که نیازمند یالهای جهتدار هستند، استفاده میشود.
- ARGC : int
- تعداد آرگومانهای مشخصشده با آرگومان خط فرمان -a args را نشان میدهد.
- ARGV : string array
- آرایه آرگومانهای مشخصشده با آرگومان خط فرمان -a args را نشان میدهد. آرگومان i-ام توسط ARGV[i] ارائه میشود..SH "ثابتهای توکار (BUILT‐IN CONSTANTS)"
چندین ثابت نمادین توسط gvpr تعریف شده است.
- NULL : obj_t
- یک ارجاع شیء تهی، معادل با 0.
- TV_flat : tvtype_t
- یک پیمایش ساده و تخت، که در آن اشیای گراف به ترتیبی ظاهراً دلخواه پیمایش میشوند.
- TV_ne : tvtype_t
- پیمایشی که ابتدا همه گرهها و سپس همه یالها را بررسی میکند.
- TV_en : tvtype_t
- پیمایشی که ابتدا همه یالها و سپس همه گرهها را بررسی میکند.
- TV_dfs : tvtype_t
- TV_postdfs : tvtype_t
- TV_prepostdfs : tvtype_t
- پیمایش گراف با استفاده از جستجوی اولعمق بر روی گراف بدونجهت زیرین. برای انجام این پیمایش، gvpr مقدار $tvroot را بررسی میکند. اگر این متغیر همان مقداری را داشته باشد که قبلاً داشت (در ابتدا، مقدار قبلی برابر با NULL مقداردهی اولیه میشود)، gvpr صرفاً به دنبال یک گره پیمایشنشده میگردد و مؤلفه همبند آن را پیمایش میکند. از سوی دیگر، اگر $tvroot تغییر کرده باشد، مؤلفه همبند آن پیمایش خواهد شد، با این فرض که قبلاً پیمایش نشده باشد یا، اگر $tvroot برابر NULL باشد، پیمایش متوقف خواهد شد. توجه داشته باشید که با استفاده از TV_dfs و $tvroot، امکان ایجاد یک حلقه بیپایان وجود دارد.
- بهطور پیشفرض، پیمایش به صورت پیشترتیب (pre-order) انجام میشود؛ بدین معنا که یک گره قبل از تمام یالهای پیمایشنشدهاش بررسی میشود. برای TV_postdfs، تمام یالهای پیمایشنشده یک گره پیش از خود گره بررسی میشوند. برای TV_prepostdfs، یک گره دو بار بررسی میشود: یکبار قبل و یکبار بعد از تمام یالهای پیمایشنشدهاش.
- TV_fwd : tvtype_t
- TV_postfwd : tvtype_t
- TV_prepostfwd : tvtype_t
- پیمایش گراف با استفاده از جستجوی اولعمق روی گراف، تنها با دنبال کردن کمانهای رو به جلو. انتخاب ریشهها برای پیمایش همانند آنچه در بالا برای TV_dfs توضیح داده شد است. ترتیبهای مختلف بررسی مشخصشده توسط TV_fwd، TV_postfwd و TV_prepostfwd همانند مواردی هستند که توسط پیمایشهای متناظر TV_dfs، TV_postdfs و TV_prepostdfs مشخص شدهاند.
- TV_rev : tvtype_t
- TV_postrev : tvtype_t
- TV_prepostrev : tvtype_t
- پیمایش گراف با استفاده از جستجوی اولعمق روی گراف، تنها با دنبال کردن کمانهای معکوس. انتخاب ریشهها برای پیمایش همانند آنچه در بالا برای TV_dfs توضیح داده شد است. ترتیبهای مختلف بررسی مشخصشده توسط TV_rev، TV_postrev و TV_prepostrev همانند مواردی هستند که توسط پیمایشهای متناظر TV_dfs، TV_postdfs و TV_prepostdfs مشخص شدهاند.
- TV_bfs : tvtype_t
- پیمایش گراف با استفاده از جستجوی اولسطح روی گراف با نادیده گرفتن جهت یالها. برای آگاهی از نقش $tvroot، به مورد TV_dfs در بالا مراجعه کنید.
مثالها (EXAMPLES)
gvpr -i 'N[color=="blue"]' file.gv
تولید زیرگراف القاشده توسط گرهها (node‐induced) برای تمام گرههای دارای رنگ آبی.
gvpr -c 'N[color=="blue"]{color = "red"}' file.gv
تبدیل تمام گرههای آبی به قرمز.
BEGIN { int n, e; int tot_n = 0; int tot_e = 0; }
BEG_G {
n = nNodes($G);
e = nEdges($G);
printf ("%d nodes %d edges %s\n", n, e, $G.name);
tot_n += n;
tot_e += e;
}
END { printf ("%d nodes %d edges total\n", tot_n, tot_e) }
نسخهای از برنامه gc.
BEG_G { graph_t g = graph ("merge", "S"); }
E {
node_t h = clone(g,$.head);
node_t t = clone(g,$.tail);
edge_t e = edge(t,h,"");
e.weight = e.weight + 1;
}
END_G { $O = g; }
تولید یک نسخه صریح (strict) از گراف ورودی، که در آن صفت weight یک یال نشان میدهد که آن یال بیانگر چه تعداد یال از گراف ورودی است.
BEGIN {node_t n; int deg[]}
E{deg[head]++; deg[tail]++; }
END_G {
for (deg[n]) {
printf ("deg[%s] = %d\n", n.name, deg[n]);
}
}
محاسبه درجه گرههای دارای یال.
BEGIN {
int i, indent;
int seen[string];
void prInd (int cnt) {
for (i = 0; i < cnt; i++) printf (" ");
}
}
BEG_G {
$tvtype = TV_prepostfwd;
$tvroot = node($,ARGV[0]);
}
N {
if (seen[$.name]) indent--;
else {
prInd(indent);
print ($.name);
seen[$.name] = 1;
indent++;
}
}
چاپ پیمایش اولعمق گراف، با شروع از گرهای با نام ARGV[0]، به صورت یک فهرست دارای تورفتگی..SH "محیط (ENVIRONMENT)"
- GVPRPATH
- فهرستی از دایرکتوریهای جداشده با دونقطه (“:”) که برای یافتن فایل مشخصشده با گزینهٔ -f جستجو میشوند. gvpr یک فهرست پیشفرض داخلی دارد. اگر GVPRPATH تعریف نشده باشد، از فهرست پیشفرض استفاده میشود. اگر GVPRPATH با دونقطه آغاز شود، فهرست با افزودن GVPRPATH به انتهای فهرست پیشفرض تشکیل میشود. اگر GVPRPATH با دونقطه پایان یابد، فهرست با افزودن فهرست پیشفرض به انتهای GVPRPATH تشکیل میشود. در غیر این صورت، از GVPRPATH برای فهرست استفاده میشود.
در سیستمهای Windows، در بند پیشین “semicolon” (نقطهویرگول) را جایگزین “colon” (دونقطه) کنید.
گزارش باگها و هشدارها (BUGS AND WARNINGS)
اسکریپتها هنگام حذف گرهها در طول بلوکهای N{} و E{} با استفاده از پیمایشهای BFS و DFS باید محتاط باشند، زیرا این پیمایشها بر پشتهها و صفهای گرهها متکی هستند.
هنگامی که برنامه به عنوان یک آرگومان خط فرمان ارائه میشود، تفسیر معمول پوسته رخ میدهد که ممکن است بر برخی از نامهای ویژه در gvpr تأثیر بگذارد. برای جلوگیری از این موضوع، بهتر است برنامه درون علامتهای نقلقول تکی (single quotes) قرار گیرد.
اگر ثابتهای رشتهای حاوی فرانویسههای الگو هستند و میخواهید برای جلوگیری از تطبیق الگو آنها را گریزدهی (escape) کنید، احتمالاً استفاده از دو بکاسلش ضروری خواهد بود؛ زیرا هنگام پویش اولیهٔ رشته، یک بکاسلش منفرد از بین میرود. معمولاً برای اجتناب از تطبیق الگو، استفاده از strcmp سادهتر است.
از ۲۴ آوریل ۲۰۰۸، gvpr به استفاده از یک کتابخانهٔ گراف زیرینِ جدید روی آورد که از مدل سادهتری استفاده میکند؛ مدلی که در آن تنها یک رونوشت از یک گره وجود دارد، نه یک رونوشت به ازای هر زیرگرافی که منطقاً شامل آن است. این بدان معناست که تکرارکنندههایی مانند nxtnode نمیتوانند صرفاً با استفاده از یک آرگومان گره، یک زیرگراف را بپیمایند. به همین دلیل، پیمایش زیرگراف به توابع جدیدی با پسوند «_sg» نیاز دارد که یک آرگومان زیرگراف را نیز دریافت میکنند. نسخههای فاقد این پسوند همیشه گراف ریشه (root graph) را میپیمایند.
بهجز پارامترهای صوری توابع، تنها یک حوزهٔ سراسری (global scope) وجود دارد و حتی این پارامترها نیز میتوانند با سامانهٔ نوعها تداخل پیدا کنند. همچنین، طول عمر (extent) تمام متغیرها برابر با کل مدت اجرای برنامه است. شاید بهتر میبود که حوزهٔ دید بیانگر آشیانهبندی طبیعی بندها باشد، یا برنامه دستکم متغیرهای محلی اعلامشده را بازنشانی کند. در حال حاضر، توصیه میشود برای تمام متغیرها از نامهای متمایز استفاده شود.
اگر تابعی به یک دستور پیچیده، مانند دستور IF ختم شود که در آن هر شاخه عمل return را انجام میدهد، ممکن است بررسی نوع (type checking) با شکست مواجه شود. توابع باید در انتهای خود از یک return استفاده کنند.
کتابخانهٔ expr از مقادیر رشتهای (char*)0 پشتیبانی نمیکند. این بدان معناست که نمیتوان بین کلیدهای یال "" و (char*)0 تمایز قائل شد. برای اهداف جستجو و ایجاد یالها، ما "" را به (char*)0 تبدیل میکنیم؛ زیرا این مقدار اخیر جهت جستجوی هر یالی با ابتدا و انتهای منطبق ضروری است.
در همین رابطه، رشتههایی که به عدد صحیح (integer) تبدیل میشوند مانند اشارهگرهای char عمل میکنند و بسته به اینکه رشته صرفاً از صفر تشکیل شده باشد یا خیر، مقدار ۰ یا ۱ میگیرند. بنابراین، مقدار عبارت ((int)"2") برابر با ۱ خواهد بود.
این زبان مشکلات معمول زبان C، مانند ارجاعات معلق (dangling references) و اشتباه گرفتن '=' با '==' را به ارث برده است.
نویسندگان (AUTHORS)
Emden R. Gansner <erg@research.att.com>
همچنین ببینید (SEE ALSO)
awk(1), gc(1), dot(1), nop(1), expr(3), cgraph(3)
| 29 August 2013 |