<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0">
    <channel>
        <title>نوشته های علیرضا توکلی</title>
        <link>https://virgool.io/feed/@artav</link>
        <description>Software Development Team Lead - https://artav.ir/about/index.html</description>
        <language>fa</language>
        <pubDate>2026-07-07 12:15:04</pubDate>
        <image>
            <url>https://files.virgool.io/upload/users/31065/avatar/h2wMa8.jpeg?height=120&amp;width=120</url>
            <title>علیرضا توکلی</title>
            <link>https://virgool.io/@artav</link>
        </image>

                    <item>
                <title>بهبود عملکرد رندر در Blazor بوسیله قابلیت component virtualization - قسمت 2</title>
                <link>https://virgool.io/@artav/virtualize2-aorlw4wduzhw</link>
                <description>توجه : این مطلب برداشتی از نوشته ی Dave Brock می باشدبرای دیدن نمونه کدهای مطلب لطفا کمی صبر کنیدبرای دیدن قسمت اول مطلب بر روی (اینجا) کلیک کنیدبرای نمایش دیتاست های حجیم در ورژن دات نت 5 Blazor ، قابلیت جدیدی افزوده شده که با هم بررسی خواهیم کرد.بیایید بیشتر بررسی کنیم. تفاوت شیوه ی قبلی و شیوه جدید در تعداد زیادی از اطلاعات Load  شده در حافظه مشخص می شود. تعداد 10000  شئ از کلاس Car می سازیم (در متد OnInitializedAsync). می خواهیم در @codeاین لیست را نمایش دهیم. https://gist.github.com/mirza-developer/5f7635d9d6f3f6dac2e9a920d1cda54a تاکنون برای نمایش اطلاعات به روش زیر عمل می کردیم: https://gist.github.com/mirza-developer/07dc2b7f094a449d1cb16578af3e6944 برنامه را run می کنیم و همزمان developer tools مرورگر خود را نیز به کار می گیریم و cache مرورگر را نیز غیرفعال می کنیم. برنامه در حالتی که از حلقه for استفاده کرده ایم، بین 2 تا 4 ثانیه طول می کشد تا بالا بیاید. حال حلقه را بصورت زیر جایگزین می کنیم: https://gist.github.com/mirza-developer/a391c2095b1d088eb9a7f44c8a5e2649 در این حالت بین 1.2 تا 1.9 ثانیه نمایش اطلاعات طول می کشد که بهبود 2 برابری را نشان می دهد. حال چشم خود را از Developer tools خود بر ندارید و صفحه را scroll کنید. من در صفحه خود این کار را کرده ام:همانطور که در ویدئو می بینید، ردیف های اطلاعاتی در صفحه ثابت است و اطلاعات جدید در ردیف های قبلی جای گذاری می شوند. اما این نمایش اطلاعات قابل customize شدن است. بدین منظور پارامتر های OverscanCount، ItemsDelegate، Placeholder و ItemSizeاست.پارامتر OverscanCountاین پارامتر مشخص می کند که چند آیتم بیشتر از آنچه در صفحه قابل نمایش است در قبل و بعد render شود. پیش از این گفته بودم که خود برنامه با توجه به ابعاد صفحه نمایش کاربر، محاسبه می کند که چند آیتم در صفحه باید دیده شوند و با scroll شدن تعداد آیتم های render شده تغییر نمی کند. با عدد دادن به این پارامتر می توان مشخص کرد که چند آیتم از قبل از اولین آیتم قابل دیدن و چند آیتم بعد از آخرین آیتم قابل دیدن render شوند تا این آیتم ها در scroll های کاربر فقط نمایش یابند. با گذر از این آیتم ها، آیتم های جدید با همین شرایط render می شوند. https://gist.github.com/mirza-developer/337cf73e4791d3aa0ae82f90f2aef179 پیاده سازی Lazy Loading با استفاده از ItemsProvider و Placeholderامکان پیاده سازی سناریو Lazy Loading  با استفاده از Virtualize به خوبی در دسترس است. ItemsProvider یک Delegate  است و می توان متد هایی با ورودی ItemsProviderRequest و خروجی ItemsProviderResult به آن Assign کرد.کلاس ItemsProviderRequest مشخص کننده ی اطلاعاتی است که می خواهیم در render بعدی، آنها را به کاربر نمایش دهیم : مثلا از چه ردیف شماره چند لیست اطلاعات، به چه تعداد از آن شماره ردیف به بعد و..کلاس ItemsProviderResult مشخص کننده ی لیست اقلام اطلاعاتی است که نمایش خواهند یافت.بیاید متدی را که باید بنویسیم را ببینیم : https://gist.github.com/mirza-developer/ed717e22d1f310a3c8e1bdd81c2787e8 من با استفاده از LINQ کاری می کنم تا در هر بار فراخوانی این متد، اطلاعات مورد نظرم در صفحه  render  شوند.حال نوبت Placeholder است. اگر به کد های نوشته شده در فایل cartable.cs توجه کرده باشید می بینید برای آنکه در هنگام ساخت لیست اطلاعات، کاربر صفحه را خالی نبیند و احساس از دسترس خارج شدن برنامه به او دست ندهد از قطعه کد زیر استفاده می کردیم: https://gist.github.com/mirza-developer/b6d2b4a9e6bcc7ea98b1189a09d20042 در اینجا ما می توانیم این بلاک را حذف کنیم و کد های زیر را جایگزین کنیم : https://gist.github.com/mirza-developer/345606eaf2387ba677f7236c5f60d10d پارامتر ItemSizeبا عدد دادن به این پارامتر، اندازه هر آیتم مشخص می شود. مقدار پیش فرض آن 50px است (منبع) https://gist.github.com/mirza-developer/d488e6dce4c9056b6354c1ea3080b62f </description>
                <category>علیرضا توکلی</category>
                <author>علیرضا توکلی</author>
                <pubDate>Tue, 19 Jan 2021 09:49:19 +0330</pubDate>
            </item>
                    <item>
                <title>بهبود عملکرد رندر در Blazor بوسیله قابلیت component virtualization - قسمت 1</title>
                <link>https://virgool.io/@artav/virtualize-nwp5htqkzled</link>
                <description>توجه : این مطلب برداشتی از نوشته ی Dave Brock می باشدبرای نمایش دیتاست های حجیم در ورژن دات نت 5 Blazor ، قابلیت جدیدی افزوده شده که با هم بررسی خواهیم کرد.در کنار اینکه آمار مربوط به عملکرد و سرعت برنامه در Load صفحه، موضوع مهمی است اما آنچه که کاربر می بیند و حس می کند در نهایت مطلبی است که باید در نظر بگیریم. فرض کنید می توان آنچه اکنون نیاز است را رندر کرد و آنچه را بعدا نیاز است، همان موقع نیاز. اما کاربر نباید بابت چیزی بیش اندازه منتظر بماند.کامپوننت virtualization تکنیکی است که رندر شدن صفحه را محدود به همان بخشی می کند که قابل دیدن است. فرض کنید که قرار است که یک Table با 1000 ردیف اطلاعاتی را به کاربر نمایش دهید. قطعا همه ی 1000 ردیف را یکجا در دسترس او قرار نمی دهید (به انتهای صفحه نمی رسد!) و با تکنیک هایی مانند Pagination به او قابلیت مدیریت نمایش تعداد اطلاعات را به او می دهید تا در صفحه گم نشود و مابقی اطلاعات را نامرئی می کنید. بدین منظور کامپوننت از پیش ساخته شده Virtualize در دسترس استفرض کنید که میخواهیم یک لیست از جنس کلاس (یا record) Person که شامل Property های FirstName و LastName را در فایل .razorکامپوننت مدنظر نمایش دهیم. کاری که باید قبلا می کردیم کد زیر بود :@foreach (var person in people)
{
    &lt;p&gt;
        @person.FirstName @person.LastName isonly fun on Fridays.
    &lt;/p&gt;
}با کامپوننت Virtualize، لیست مورد نظر را به Items پاس می دهیم و با استفاده از context به اطلاعات آبجکت دسترسی داریم&lt;Virtualize Items=&amp;quot@people&amp;quot&gt;
    &lt;p&gt;
        @context.FirstName @context.LastName is only fun on Fridays.
    &lt;/p&gt;
&lt;/Virtualize&gt;به علاوه اگر بخواهیم context را در برنامه خود صریحا تعریف کنیم می توانیم از کد زیر استفاده کنیم&lt;Virtualize Context=&amp;quotperson&amp;quot Items=&amp;quot@people&amp;quot&gt;
    &lt;p&gt;
        @person.FirstName @person.LastName is only fun on Fridays.
    &lt;/p&gt;
&lt;/Virtualize&gt;کامپوننت Virtualizeتلاش می کند تا بفهمد که ارتفاع container ای که در آن عمل می کند و ارتفاع هر آیتم را که میخواهد رندر می شود چقدر است. منظور از &quot; container&quot; می تواند یک یا چند کامپوننت Razor، ترکیبی از HTML و کامپوننت های Razor یا یک کد Razorساده باشد.تا اینجا ساده ترین نوع استفاده را دیدیم. این کامپوننت می تواند موارد استفاده ی پیشرفته تر و وسیع تری داشته باشد.بزودی در این باره بیشتر خواهم گفت</description>
                <category>علیرضا توکلی</category>
                <author>علیرضا توکلی</author>
                <pubDate>Fri, 08 Jan 2021 22:59:18 +0330</pubDate>
            </item>
                    <item>
                <title>همزمانی در توسعه نرم افزار</title>
                <link>https://virgool.io/@artav/concurrency-jgq0ythljh4r</link>
                <description>توجه : این نوشته برداشتی از کتاب Concurrency in C# Cookbook نوشته Stephen Cleary می باشدقبل از هر چیز، بهتر است واژگانی که در ادامه از آنها استفاده خواهیم کرد را شفاف کنیم. اینها تعریف هایی است که من بصورت معمول از آنها برای ابهام زدایی از اصطلاحات برنامه نویسی استفاده می کنم.همزمانی: انجام بیش از یک کار در یک زمانبه نظرم مشخص شد که چرا همزمانی، یک تکنیک بدردبخور است. برنامه های End-user از همزمانی برای نوشتن روی پایگاه داده، در حین پاسخ دادن به ورودی های کاربر استفاده می کنند. برنامه های سمت سرور، از همزمانی برای پاسخ دادن به Request دوم در حین تمام کردن Request اول استفاده می کنند. به همین ترتیب هر برنامه مناسب با کاری که می خواهد انجام بدهد، از همزمانی استفاده می کند تا بتواند روی بیشتر از یک کار را در زمانی که کار دیگری انجام می دهد، پردازش کند. تمام برنامه های نوشته شده در دنیا می توانند از مزایای همزمانی بهره ببرند.زمانی که از همزمانی صحبت می کنیم، بیشتر توسعه دهندگان، بی درنگ، به یاد برنامه نویسی چند نخی (MultiThreading) می افتند. دوست دارم میان این دو تمایزی ایجاد کنم.برنامه نویسی چند نخی (MultiThreading) : شکلی از همزمانی که در آن از چندین Thread به جز Thread اصلی برای انجام کار استفاده می شودهمانطور که در ادامه خواهیم دید، MultiThreading یکی از راه های ایجاد همزمانی در نرم افزار است ولی به طور قطع تنها راه نیست. در حقیقت استفاده مستقیم از شکل های سطح پائین Threading، در برنامه های مدرن جایی ندارند، شکل های سطح بالاتر، نه تنها قدرتمندترند، بلکه سود بیشتری از شکل های قدیمی دارند. به همین خاطر درباره تکنیک های تاریخ گذشته کمتر صحبت خواهم کرد. هیچ کدام از دستورالعمل های این کتاب، از تایپ های Thread و BackgroundWorkerاستفاده نمی کنند، در عوض از جایگزین های برتری سخن خواهم گفت.اما، اصلا فکر نکنید که ایده ی MultiThreadingمرده است. MultiThreading در thread pool زنده است. جایی که صف کار، بصورت اتوماتیک و براساس تقاضا، فعالیت ها را تنظیم می کند.  thread pool قایلیت ایجاد یک نوع همزمانی دیگر به نام پردازش موازی (Parallel processing) را فراهم می کند.پردازش موازی (Parallel processing): مقدار زیادی از کارها را با استفاده از تقسیم آنها در چند نخ (Thread) به صورت همزمان انجام دهیم.پردازش موازی (یا برنامه نویسی موازی) از MultiThreading کمک می گیرد تا از استفاده از توان هسته های پردازنده را حداکثر کند. پردازنده های مدرن، هسته های متعددی دارند و اگر کار های زیادی برای انجام دادن موجود باشد، معنی ندارد که همه ی کار ها را یک هسته انجام دهد و بقیه بیکار باشند! پردازش موازی کار ها را میان چند Thread تقسیم می کند که می توانند مستقل روی چند هسته مختلف اجرا شوند.پردازش موازی، یکی از انواع روش های MultiThreading است و MultiThreading، یکی از روش های ایجاد همزمانی. نوع دیگری نیز وجود دارد که با وجود اهمیتش در برنامه های مدرن، برای برخی از توسعه دهندگان آشنا نیست. برنامه نویسی ناهمگام (Asynchronous programming).برنامه نویسی ناهمگام : یکی از انواع همزمانی که در آن از future ها و یا callback ها برای جلوگیری کردن از ایجاد thread های غیر لازم استفاده می شود.تایپ های future (یا promise) مشخص کننده ی فعالیت هایی هستند که در آینده تکمیل خواهند شد. در برنامه های مدرن .net از Task and Task&lt;TResult&gt; استفاده می شود. برنامه های قدیمی تر از callback و Event ها به جای از future استفاده می کردند.برنامه نویسی ناهمگام، حول ایده ی Asynchronous operation (عملیات های ناهمگام) چیده شده است، به این مفهوم که برخی عملیات ها که هم اکنون شروع شده اند، در آینده به اتمام خواهند رسید. بنابراین، تا زمانی که عملیات در حال انجام است، کار Threadاصلی برنامه، با وقفه رو به رو نگردد(منوط به اتمام عملیات نشود). بنابراین، Thread اصلی برنامه ظرفیت دارد تا کار دیگری را انجام دهد. زمانی که  عملیات به اتمام رسید، به future خود اطلاع می دهد ویا  eventیا callback خود را فعال میکند تا برنامه بداند کار تمام شده است.برنامه نویسی ناهمگام،  یک حالت قدرتمند از همزمانی است اما تا قبل از این نیاز به کدهای بسیار پیچیده ای داشت. با استفاده از async  و  await به راحتی حالت synchronous (همگام) می توان برنامه نوشت.فرم دیگری از همزمانی، Reactive programming (برنامه نویسی واکنشی) است. Asynchronous programming یک عملیاتی را شروع می کند که در آینده تمام خواهد شد و همان زمان به سراغ آن خواهد رفت. Reactive programming بسیار شبیه به Asynchronous programming است باید تفاوت که Asynchronous programming از Asynchronous operation ها استفاده می کند ولی Reactive programming از Asynchronous events (رویداد های ناهمگام) استفاده می کند. Asynchronous events ممکن است در زمان مشخصی شروع نشوند و چندین بار فرخوانی شوند. مانند ورود اطلاعات توسط کاربر.برنامه نویسی واکنشی : یک فرم مشخص کردن محل و نحوه واکنش برنامه به Event هااگر یک برنامه را یک ماشین حالت بزرگ در نظر بگیریم، رفتار برنامه می تواند واکنش هایی به یک سری از رویداد ها تلقی شود که در هر Event یک حالت بروز می شود.این ققط یک مفهوم تئوری یا انتزاع نیست. Framework های مدرن از این رویکرد بصورت کاملا مفید در برنامه های واقعی استفاده می کنند. Reactive programming الزاما همزمان نیست، ولی به چیزی که در ادامه می خواهیم توضیح بدهیم بسیار مربوط است.بهترین راه حل، استفاده از مخلوطی از این موارد برحسب استفاده است.</description>
                <category>علیرضا توکلی</category>
                <author>علیرضا توکلی</author>
                <pubDate>Wed, 06 Jan 2021 23:45:38 +0330</pubDate>
            </item>
            </channel>
</rss>