<?xml version="1.0" encoding="UTF-8"?><rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>annotation &#8211; Mahdi Tajik</title>
	<atom:link href="http://www.mahditajik.ir/tag/annotation/feed/" rel="self" type="application/rss+xml" />
	<link>http://www.mahditajik.ir</link>
	<description>I&#039;m Mahdi Tajik. I am project manager and Full-stack Android developer. welcome to my personal website.</description>
	<lastBuildDate>Thu, 29 Nov 2018 14:21:09 +0000</lastBuildDate>
	<language>fa-IR</language>
	<sy:updatePeriod>
	hourly	</sy:updatePeriod>
	<sy:updateFrequency>
	1	</sy:updateFrequency>
	<generator>https://wordpress.org/?v=6.2.6</generator>

<image>
	<url>http://www.mahditajik.ir/wp-content/uploads/2015/03/cropped-sample-logo-MT-2-32x32.png</url>
	<title>annotation &#8211; Mahdi Tajik</title>
	<link>http://www.mahditajik.ir</link>
	<width>32</width>
	<height>32</height>
</image> 
	<item>
		<title>کار با Dagger2 به زبان ساده  بخش دوم (پیشرفته)</title>
		<link>http://www.mahditajik.ir/dagger2-advanced-example/</link>
					<comments>http://www.mahditajik.ir/dagger2-advanced-example/#comments</comments>
		
		<dc:creator><![CDATA[mahdi]]></dc:creator>
		<pubDate>Sat, 01 Jul 2017 15:30:09 +0000</pubDate>
				<category><![CDATA[آموزش]]></category>
		<category><![CDATA[annotation]]></category>
		<category><![CDATA[Dagger]]></category>
		<guid isPermaLink="false">http://www.mahditajik.ir/?p=2249</guid>

					<description><![CDATA[<p>سلام دوستان عزیز، متاسفانه کمی طول کشید تا مطلب آموزشی بگذارم، کامنت ها و استقبال شما انرژی خاصی به من داد تا هرچه زود تر نسبت به کامل کردن این بحث اقدام کنم. خیلی خوب، در مقاله قبلی با نحوه استفاده از Dagger2 آشنا شدیم. در این بخش می خواهیم چند روش دیگر استفاده را ...</p>
<p>نوشته <a rel="nofollow" href="http://www.mahditajik.ir/dagger2-advanced-example/">کار با Dagger2 به زبان ساده  بخش دوم (پیشرفته)</a> اولین بار در <a rel="nofollow" href="http://www.mahditajik.ir">Mahdi Tajik</a> پدیدار شد.</p>
]]></description>
										<content:encoded><![CDATA[<p><img decoding="async" loading="lazy" class="aligncenter size-full wp-image-2424" src="http://www.mahditajik.ir/wp-content/uploads/2017/07/dagger2_2.jpg" alt="" width="800" height="486" srcset="http://www.mahditajik.ir/wp-content/uploads/2017/07/dagger2_2.jpg 800w, http://www.mahditajik.ir/wp-content/uploads/2017/07/dagger2_2-300x182.jpg 300w, http://www.mahditajik.ir/wp-content/uploads/2017/07/dagger2_2-768x467.jpg 768w" sizes="(max-width: 800px) 100vw, 800px" /></p>
<p style="text-align: justify;">سلام دوستان عزیز، متاسفانه کمی طول کشید تا مطلب آموزشی بگذارم، کامنت ها و استقبال شما انرژی خاصی به من داد تا هرچه زود تر نسبت به کامل کردن این بحث اقدام کنم. خیلی خوب، در <span class="highlight"><a href="http://www.mahditajik.ir/dagger2-simple-example/" target="_blank" rel="noopener"><strong>مقاله قبلی</strong></a></span> با نحوه استفاده از Dagger2 آشنا شدیم. در این بخش می خواهیم چند روش دیگر استفاده را به همراه امکانات بیشتر این کتابخانه مورد برسی قرار دهیم. همانطور که در آموزش قبلی به روز کردم به علت استفاده زیاد از این کتابخانه، گوگل امکان اضافه کردن آن را به صورت مستقیم داده و شما می توانید ازین پس بصورت زیر در gradle در سطح خود برنامه از آن استفاده کنید:</p>
<pre class="crayon-plain-tag">compile 'com.google.dagger:dagger:2.7'
annotationProcessor 'com.google.dagger:dagger-compiler:2.7'</pre>
<p style="text-align: justify;">می خواهیم کمی بیشتر با DI آشنا شویم و ابزار های آن را در Dagger2 ببینیم. ما چند نوع تزریق داریم.</p>
<h4 id="constructor-injection"><strong>Constructor injection</strong></h4>
<p>برروی کانستراکتور Inject@ گذاشته و در این صورت دیگر نیازی به نوشتن Module نداریم.</p>
<h4 id="fields-injection"><strong>Fields injection</strong></h4>
<p>همینطور که در آموزش قبل ملاحظه کردید تزریق یک فیلد را گویند. ( در تمامی آموزش قبل از fields injection استفاده کردیم)</p>
<h4 id="methods-injection"><strong>Methods injection</strong></h4>
<p>بروری یک متدی از یک کلاس Inject@ بگذاریم.</p>
<p>&nbsp;</p>
<p><span style="color: #99cc00;"><strong>چند انوتیشن که باید در این جلسه با آنها آشنا شویم:</strong></span><br />
<pre class="crayon-plain-tag">@Scope annotation</pre>
<p style="text-align: justify;">اصولا هدف استفاده از این انوتیشن معرفی <strong>Scope</strong> آبجک تولید شده است. یعنی <strong>Dagger2</strong> به شما این امکان را می دهد تا <strong>Object</strong> های شما چرخه عمر متفاوت داشته باشند و شما فقط تعریف می کنید، مدیریتش با خود <strong>Dagger</strong> است. پیشنهاد من این است که برای این مقاله تا همین حد کافی است و بعد از اتمام این اموزش به <span class="highlight"><a href="http://www.mahditajik.ir/dagger2-custom-scopes/" target="_blank" rel="noopener">مقاله کامل</a></span> مراجعه کنید.</p>
<pre class="crayon-plain-tag">@Qualifier</pre>
<p style="text-align: justify;">وقتی از این انوتیشن استفاده می کنیم که متد ها همنام و و ورودی خروجی یکسان داشته باشند و به <strong>Dagger</strong> می فهمانیم کِی، چی را تزریق کند.</p>
<p style="text-align: justify;">بسیار عالی. در آموزش قبل دیدیم که هرجا بخواهیم از <strong>DI</strong> توسط <strong>Dagger2</strong> استفاده کنیم باید سه مرحله زیر را انجام دهیم:</p>
<p style="text-align: justify;">۱- ساخت <strong>Provider</strong> ها در کلاس <strong>Module</strong> که مشخص می کنیم کلاس ها چگونه تولید شوند.</p>
<p style="text-align: justify;">۲- ساخت اینترفیسی به نام <strong>Component</strong> که می گویم از کدام <strong>Module</strong> ها استفاده کند و متدی در آن قرار می دادیم که کلاسی که در آن <strong>Inject</strong> انجام شده بود وجود داشته باشد تا <strong>Dagger2</strong> بفهمد کدام کلاس ها را جهت فیلد انجکشن اسکن و وایراپ کند و متوجه شدیم که <strong>Dagger</strong> متدها رو بصورت خودکار تولید می کند.</p>
<p style="text-align: justify;">۳- در کلاس استفاده کننده ( قرار است <strong>Inject</strong> اتفاق بیافتد) متد تعریف شده در <strong>Component</strong> را از کلاس <strong>AutoGenerated</strong> توسط <strong>Dagger</strong> صدا بزنیم و  تمام!</p>
<p style="text-align: justify;">اگر هنوز بخش مبهمی مانده با در نظر گرفتن سه مرحله بالا<span style="color: #3366ff;"> <a href="http://www.mahditajik.ir/dagger2-simple-example/" target="_blank" rel="noopener"><strong>آموزش قبل</strong> </a></span>را دوباره مطالعه کنید.</p>
<p><img decoding="async" loading="lazy" class="aligncenter size-full wp-image-2378" src="http://www.mahditajik.ir/wp-content/uploads/2017/06/dagger_general.png" alt="" width="790" height="636" srcset="http://www.mahditajik.ir/wp-content/uploads/2017/06/dagger_general.png 790w, http://www.mahditajik.ir/wp-content/uploads/2017/06/dagger_general-300x242.png 300w, http://www.mahditajik.ir/wp-content/uploads/2017/06/dagger_general-768x618.png 768w" sizes="(max-width: 790px) 100vw, 790px" /></p>
<p><span style="color: #99cc00;"><strong>حال یک سوال:</strong></span></p>
<p style="text-align: justify;">با توجه به مطالب یاد شده می توانیم هر بخش از برنامه را بصورت <strong>DI</strong> توسط <strong>Dagger2</strong> بنویسیم. مثلا یکسری کلاس هایی را بصورت <strong>Inject</strong> در کلاس های دیگر استفاده کنید. اما سوال من این است که اگر بخواهیم در کل پروژه از <strong>DI</strong> استفاده کنیم چه باید کرد؟ یعنی کلاس هایی که به همدیگر ربط پیدا می کنند. (مثلا <strong>Context</strong> که در خیلی جاها لازم داریم و یا <strong>SharedPrefrence</strong> و یا خیلی کلاس های دیگر) این سوالی بود که برای خودم هم پیش آمد و بهترین جواب برای آن طراحی از بالا به پایین کل پروژه است! یعنی به جای اینکه بیاییم  از پایین به بالا برای تک تک کلاس های استفاده شده <strong>Module</strong> بنویسیم و سپس برسیم به سطح کامپوننت های اندروید مثل <strong>fragment</strong> و <strong>Activity</strong> که واقعاً نشدنی است و ارتباطات خیلی پیچیده می شود و از طرفی <strong>Inject</strong> های تکراری ایجاد می شد که <strong>Dagger2</strong> آن را قبول نمی کند، بهتر است از سطح <strong>Application</strong> به پایین طراحی کنیم. این نکته را هم در نظر داشته باشید که <strong>Dagger2</strong> در یک <strong>DI</strong> مجزا، امکان ساخت یک کامپوننت اصلی را می دهد ( به شکل بالا توجه کنید) و اگر کامپوننت های دیگری داشتیم باید در ارتباط با کامپوننت اصلی باشند.  ( این ارتباط یا از نوع <span style="color: #00ccff;"><strong>Dependency</strong></span> است یا <span style="color: #00ccff;"><strong>SubComponent</strong> </span>که در انتهای این بحث به تفاوت آنها اشاره خواهم کرد.) البته این مساله در صورتی است که <strong>Dependency Injection</strong> های مرتبط به هم داشته باشید. اما اگر فقط می خواهید در بخش های خاصی از برنامه از <strong>DI</strong> استفاده کنید که به هم مرتبط نیستند هر کدام <strong>Component</strong> و <strong>Module</strong> مستقل از هم را خواهند داشت که مشکلی هم پیش نمیاید. مثلا در مساله آموزش قبل که DI را برای تولید خودرو استفاده کردیم، فرض کنید یک <strong>DI</strong> هم برای قایق یا کشتی بنویسیم که بخواهیم تولید قایق را برایمان مدیریت کند. برای این کار دقیقاً مانند <strong>DI</strong> خودرو <strong>Module</strong> و <strong>Component</strong> مربوطه آن را تشکیل می دهیم و ربطی هم به <strong>DI</strong> خودرو ندارد و از هم مستقل اند. تنها نقطه مشترک کلاسی هست که استفاده کننده است. ( مانند <strong>Activity</strong>)</p>
<p>&nbsp;</p>
<p style="text-align: justify;">می خواهیم مثالی ساده نوشته و  آن را باهم برسی کنیم. لطفاً به این بخش خیلی توجه کنید. به علت ارتباط بخش های مختلف ممکن است پیچیدگی ظاهری داشته باشد، اما واقعاً پیچیده نیست و تمامی قوانینی که در جلسه قبل گفتیم صادق است. تلاش من این است که تمامی حالت های ممکن برای ساخت <strong>DI</strong> را برسی کنیم تا تمامی سوالات برطرف شود.</p>
<p><span style="color: #99cc00;"><strong>شرح برنامه:</strong></span></p>
<p style="text-align: justify;">برنامه ای داریم که با استفاده از اطلاعات کاربری، درخواستی به وب زده و نتیجه را در پایگاه داده ذخیره می کند. توجه کنید که اتفاقات بصورت شماتیک است و هدف برسی روابط آنها در <strong>Dagger2</strong> می باشد و صرفاً به ازای اکثر عملیات ها در کد، فقط لاگ کرده ایم. به شکل زیر دقت کنید: کلاس اپلیکیشن دارای کلاس های <strong>Context</strong> و <strong>User</strong> و <strong>Database</strong> (که وابسته به Context  و User است) و <strong>Activity</strong> است و خود کلاس Activity هم شامل NetworkCalss است که  وابسته به <strong>User </strong>است.</p>
<p><img decoding="async" loading="lazy" class="aligncenter size-full wp-image-2382" src="http://www.mahditajik.ir/wp-content/uploads/2017/07/photo_2017-07-01_12-23-49.jpg" alt="" width="1280" height="800" srcset="http://www.mahditajik.ir/wp-content/uploads/2017/07/photo_2017-07-01_12-23-49.jpg 1280w, http://www.mahditajik.ir/wp-content/uploads/2017/07/photo_2017-07-01_12-23-49-300x188.jpg 300w, http://www.mahditajik.ir/wp-content/uploads/2017/07/photo_2017-07-01_12-23-49-768x480.jpg 768w, http://www.mahditajik.ir/wp-content/uploads/2017/07/photo_2017-07-01_12-23-49-1024x640.jpg 1024w" sizes="(max-width: 1280px) 100vw, 1280px" /></p>
<p><span style="color: #99cc00;"><strong>نکات برنامه:</strong></span></p>
<p style="text-align: justify;">کلاس <strong>Application</strong> به <strong>Database</strong> نیاز دارد تا آن را در اول برنامه <strong>Initilize</strong> کند از طرفی <strong>Database</strong> به <strong>User</strong> و <strong>Context</strong> نیاز دارد. سپس <strong>Activity</strong> یک <strong>Network Request</strong> می زند و نتیجه را در <strong>Database</strong> ذخیره می کند.اول از همه <strong>Module</strong> های مربوط به <strong>User</strong> و <strong>Database</strong> را ایجاد می کنیم تا <strong>Dagger</strong> بفهمد آنها را چگونه تولید کند.</p>
<pre class="crayon-plain-tag">@Module
public class UserModule {

    @Provides
    @Singleton
    User providesUser() {
        return new User("Farhad", "Majidi");
    }
}

@Module
public class DatabaseModule {

    @Singleton
    @Provides
    Database providesDatabase(Context context,User user){
        return new Database(context,user);
    }
}

@Singleton
@Component(modules = {ApplicationModule.class, DatabaseModule.class,UserModule.class})
public interface ApplicationComponent {

    void inject(DaggerTestApplication application);


    // Exported for child-components. (subcomponent need this to use Context or User or Database)

    Context getContext();

    User provideUser();

    Database provideDatabase();

}</pre>
<img decoding="async" loading="lazy" class=" wp-image-2394 alignright" src="http://www.mahditajik.ir/wp-content/uploads/2017/07/simple.jpg" alt="" width="144" height="48" /></p>
<p style="text-align: justify;"><span style="color: #ff9900;">سوال: چه چیزی را می خواهیم تزریق کنیم؟</span> جواب: <strong>DataBase</strong> و <strong>User</strong></p>
<p style="text-align: justify;"><span style="color: #ff9900;">سوال: چطور ساخته می شود؟</span> جواب: در <strong>UserModule </strong> و <strong>DatabaseModule</strong> مشخص شده است و آنها را به عنوان <strong>Module</strong> به <strong>Component</strong> داده ایم!</p>
<p style="text-align: justify;"><span style="color: #ff9900;">سوال: استفاده کننده نهایی کیست؟</span> جواب: <strong>DaggerTestApplication </strong> است بنابر این یک متد با ورودی خودش نوشتیم تا Inject@ های روی فیلدهایش اسکن شود.</p>
<p style="text-align: justify;"><span style="color: #ff9900;">سوال: دوسه تا متد بعدی چیه؟</span> جواب: باید برای هر کلاسی که child ها به آن نیاز دارند یک متد Exporter  بنویسیم.</p>
<p style="text-align: justify;">از آنجایی که می خواهم کلاس <strong>NetworkClass</strong> را فقط در <strong>Activity</strong> استفاده کنم و از طرفی <strong>NetworkClass</strong> به User نیاز دارد بنابراین یک کامپوننت جدا با <strong>Scope</strong> جدید می نویسیم. چون می خواهم مادامی که Activity وجود دارد <strong>NetworkClass</strong> نیز وجود داشته باشد. اما لازم است تا <strong>Component</strong> اصلی متدهایی داشته باشند تا کلاس <strong>User</strong> را برایم <strong>Export</strong> کنند. بنابر این من متدی اضافه کردم به نام <strong>provideUser </strong>که خروجی آن<strong> User </strong>است. خود <strong>Dagger</strong> پیداده سازی آن را مدیریت می کند. همچنین چون ممکن است <strong>Context</strong> برنامه را کلاس های دیگر بخواهند یک متد نیز برای آن نوشتیم و همچنین برای <strong>Database</strong> هم یک متد <strong>Export</strong> کننده نوشتم.( خواهید دید که <strong>DataBase</strong> در <strong>Activity</strong> جهت ذخیره مورد نیاز قرار خواهد گرفت. پس یک متد <strong>Export</strong> کننده لازم داشت.) این طراحی بالا به پایینی بود که اول مقاله گفتم. یعنی در <strong>Component</strong> اصلی که نحوه ارتباط ها را مشخص می کنیم برای فرزند ها نیز وابستگی های مشترک را در نظر بگیریم.</p>
<p style="text-align: justify;">یک نکته دیگر در مورد context است. از آنجایی که کلاس های دیگری ممکن است به آن وابسته شوند یک متد برای آن نوشتیم، اما چون Context را ما نمی سازیم و خود سیستم تولید می کند لازم نیست برایش Module بنویسیم و ساخت و Handle آن توسط خود Dagger با Android system انجام می شود. البته در این پروژه استفاده ای از آن نکردیم، اما مطمئناً به آن نیاز پیدا خواهید کرد.</p>
<p style="text-align: justify;">حال می رویم سراغ وابستگی های <strong>Activity</strong> و این بخش است که کمی برایمان تازگی دارد.</p>
<pre class="crayon-plain-tag">@Scope
@Retention(RetentionPolicy.RUNTIME)
public @interface ActivityScope {
}


@Module
public class ServiceModule {

    @ActivityScope
    @Provides
    NetworkClass providesNetworkClass(User user) {
        return new NetworkClass(user);
    }
}

@ActivityScope
@Component(dependencies = ApplicationComponent.class, modules = ServiceModule.class)
public interface ActivityComponent {

    void inject(MainActivity activity);

}</pre>
<strong><img decoding="async" loading="lazy" class="alignright wp-image-2394 " src="http://www.mahditajik.ir/wp-content/uploads/2017/07/simple-300x100.jpg" alt="" width="156" height="52" /></strong></p>
<p style="text-align: justify;"><span style="color: #ff9900;">سوال: چه چیزی را می خواهیم تزریق کنیم؟</span> جواب: <strong>NetworkClass</strong></p>
<p style="text-align: justify;"><span style="color: #ff9900;">سوال: چطور ساخته می شود؟</span> جواب: در <strong>ServiceModule</strong> مشخص شده است و آن را به عنوان <strong>Module</strong> به <strong>Component</strong> داده ایم!</p>
<p style="text-align: justify;"><span style="color: #ff9900;">سوال: اما نحوه ساخت یوزر را در ServiceModule  نداریم؟!</span> جواب: در <strong>ActivityComponent </strong> مشخص کردیم که</p>
<p style="text-align: justify;"><strong>dependencies = ApplicationComponent.class</strong> ( یعنی وابستگی به <strong>ApplicationComponent</strong> داریم و هر کلاسی که در آن <strong>Export</strong> شده است را می توانیم استفاده کنیم. پس <strong>ServiceModule</strong> در ساخت <strong>NetworkClass</strong> یک <strong>User</strong> به عنوان ورودی می گیرد، و نحوه ساخت آن یوزر را <strong>ApplicationComponent </strong> می داند.</p>
<p style="text-align: justify;"><span style="color: #ff9900;">سوال: چرا Scope جدید دادیم؟</span> جواب: برای اینکه می خواهیم مادامی که استفاده کننده آن (Activity ) وجود دارد، <strong>NetworkClass</strong> ما وجود داشته باشد. نحوه دقیق کار Scope <span class="highlight"> <a href="http://www.mahditajik.ir/dagger2-custom-scopes/" target="_blank" rel="noopener">در این آموزش</a></span> موجود است.</p>
<p style="text-align: justify;"><span style="color: #ff9900;">سوال: این NetworkClass کجا استفاده می شود و Dagger از کجا می فهمد؟</span> جواب: این جواب رو دیگه شما هم می دانید و همانطور که در کلاس <strong>Activity</strong> ملاحظه می کنید چون درون دوتا فیلد اینجکشن داریم ( یکی <strong>NetworkClass</strong> و دیگری <strong>DataBase</strong>)  بنابر این یک متدی در <strong>Component</strong> قرار دادم تا ورودی آن از جنس <strong>MainActivity</strong> باشد تا تمامی Field injection های آن اسکن شود و ارتباط ها برقرار شود.</p>
<pre class="crayon-plain-tag">public class MainActivity extends AppCompatActivity {

 
    @Inject
    NetworkClass networkClass;

    @Inject
    Database database;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        initialize();
        webRequest();

    }

    private void webRequest() {

        networkClass.request("https://google.com");
        database.saveToDB();
    }

    private void initialize() {

        ((DaggerTestApplication)getApplicationContext()).getActivityComponent().inject(this);
    }


}</pre>
<p style="text-align: justify;">ملاحظه خواهید کرد که هم <strong>NetworkClass</strong> و هم <strong>DataBase</strong> به درستی در <strong>Activity</strong> تزریق شده اند و قابل استفاده هستند. حالا که نحوه کار با <strong>Dagger2</strong> را متوجه شدیم می توانیم برای متوجه شدن بیشتر این کد را به چند صورت متفاوت نوشت و تغییر داد. که همه اینها در <strong>Github</strong> در شاخه های با نام های:<span style="color: #000000;">lesson2, lesson2-type2, lesson2-type3, lesson2-subcomponent</span> قرار گرفته اند.</p>
<p>&nbsp;</p>
<p><span style="color: #99cc00;"><strong>روش های دیگر برای درک کامل</strong></span></p>
<p style="text-align: justify;">برای اینکه دقیقاً بفهمید Dagger2 چطور کار می کند حتماً این مثال ها را ببینید و درک کنید. <span class="highlight">در این چند مثال انواع روش های پیاده سازی را انجام داده ام و فهمیدن انها باعث از بین رفتن گنگی نسبی قضیه و تسلط کامل خواهد شد و جواب بسیاری از سوال هایی که در ذهن دارید را خواهید یافت</span>. تلاشم تغییر روی یک کلاس واحد Database بود تا با ثابت بودن آن تغییر روش ها را ملاحظه نمایید.</p>
<p style="text-align: justify;"><span style="color: #00ccff;">شاخه lesson2 :</span> همین کدی است که در این آموزش داشتیم.</p>
<p style="text-align: justify;"><span style="color: #00ccff;">شاخه lesson2-type2</span> :در کلاس Database خود User تزریق شده است. بنابراین ناچاریم تا متدی بنویسیم که ورودی آن Database باشد تا فیلد های تزریق شده اسکن شود.</p>
<p style="text-align: justify;"><span style="color: #ff0000;"><span style="color: #00ccff;">شاخه lesson2-type3:</span> <span style="color: #000000;">در کلاس Database از Constructor Injection استفاده کردم. همانطور که در تعریف اول بحث مطرح کردم در این روش Inject@ در روی Constructor  کلاس می گذاریم و دیگر نیازی به نوشتن Module برای نحوه پیاده سازی آن نداریم و کلا DatabaseModule حذف می شود. البته ActivityComponent تغییری نمی کند.</span><br />
</span></p>
<pre class="crayon-plain-tag">public class Database {

    private static final String TAG = "mahditajik.ir";

    @Inject
    User user;
    private Context context;

    @Inject
    public Database(Context context) {
        this.context = context;

    }

    public void initialize() {
        Log.i(TAG, "initialize with context: " + context.toString());

    }

    public void saveToDB() {
        Log.i(TAG, "saveToDB: " + user.toString());
    }
}

@Singleton
@Component(modules = {ApplicationModule.class,UserModule.class})
public interface ApplicationComponent {

    void inject(DaggerTestApplication application);

    // Exported for child-components.

    Context getContext();

    User provideUser();

    //because it had Constructor injected and do not need for Module or exporter
//    Database provideDatabase();

}</pre>
<span style="color: #00ccff;">شاخه lesson2-subcomponent</span> : مثالی است در مورد مطلب مهمی که در اواسط آموزش به آن اشاره کردم:</p>
<h3><span style="color: #99cc00;"><strong>Subcomponent vs Dependency</strong></span></h3>
<p style="text-align: justify;">همانطور که در مثال ملاحظه کردید برای ارتباط <strong>ActivityComponent</strong> با <strong>ApplicationComponent</strong> از <strong>Dependencies</strong> استفاده کردیم</p>
<pre class="crayon-plain-tag">@Component(dependencies = ApplicationComponent.class, modules = ServiceModule.class)</pre>
<p style="text-align: justify;">و سپس هر <strong>Object</strong> که لازم بود را در <strong>ApplicationComponent</strong> برایش یک متد <strong>exporter</strong> نوشتیم. اما راه دیگر استفاده به عنوان <strong>Subcomponent</strong> است. در این روش انترفیس <strong>subcomponent</strong> به همه <strong>Object</strong> های <strong>Component</strong> دسترسی دارد و نیازی به نوشتن متد های <strong>exporter</strong> ندارد و کارایی آن هنگامی است که واقعاً به تمامی <strong>object</strong> ها نیاز داریم. برای شناساندن <strong>Subcomponent</strong> به <strong>Component</strong> اصلی فقط کافیست که یک متد <strong>Factory</strong> برایش در <strong>Component</strong> بنویسیم.</p>
<pre class="crayon-plain-tag">@MahdiScope
@Subcomponent(modules = ServiceModule.class)
public interface ActivityComponent {

    void inject(MainActivity activity);

}

@Singleton
@Component(modules = {ApplicationModule.class, DatabaseModule.class, UserModule.class})
public interface ApplicationComponent {

    void inject(DaggerTestApplication application);


    // Exported for child-components.

//    Context getContext();
//
//    User provideUser();
//
//    Database proDatabase();


    //sub component

    ActivityComponent providesActivityComponent(ServiceModule service);

}</pre>
<p style="text-align: justify;">و برای استفاده wire-up کردن هم متد ماژول ان را از کامپوننت اصلی بگیریم. ( خط ۲۷)</p>
<pre class="crayon-plain-tag">public class MainActivity extends AppCompatActivity {

    @Inject
    NetworkClass networkClass;

    @Inject
    Database database;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        initialize();
        webRequest();

    }

    private void webRequest() {

        networkClass.request("https://google.com");
        database.saveToDB();
    }

    private void initialize() {

        ((DaggerTestApplication) getApplicationContext()).getAppComponent()
                .providesActivityComponent(new ServiceModule()).inject(this);

    }
}</pre>
<p style="text-align: justify;">امیدوارم تونسته باشم مطلب رو خوب بیان کنم. در صورت وجود هر گونه مشکل یا سوال یا بحث، که واقعاً این مبحث نیاز به بحث داره، راحت باشید و کامنت بگذارید.</p>
<p><a href="https://github.com/mahdit83/Dagger2SimpleExample" target="_blank" rel="noopener noreferrer"><img decoding="async" loading="lazy" class="aligncenter size-full wp-image-2146" src="http://www.mahditajik.ir/wp-content/uploads/2016/12/github_download.png" alt="github_download" width="230" height="70" /></a></p>
<p>بعد از گرفتن پروژه یکبار اون رو import کنید تا قابل اجرا بشه.</p>
<p>منبع: <a href="http://www.biitecode.ir" target="_blank" rel="noopener">بایت کد</a></p>
<p>نوشته <a rel="nofollow" href="http://www.mahditajik.ir/dagger2-advanced-example/">کار با Dagger2 به زبان ساده  بخش دوم (پیشرفته)</a> اولین بار در <a rel="nofollow" href="http://www.mahditajik.ir">Mahdi Tajik</a> پدیدار شد.</p>
]]></content:encoded>
					
					<wfw:commentRss>http://www.mahditajik.ir/dagger2-advanced-example/feed/</wfw:commentRss>
			<slash:comments>14</slash:comments>
		
		
			</item>
		<item>
		<title>برسی Scope@ ها در Dagger2</title>
		<link>http://www.mahditajik.ir/dagger2-custom-scopes/</link>
					<comments>http://www.mahditajik.ir/dagger2-custom-scopes/#comments</comments>
		
		<dc:creator><![CDATA[mahdi]]></dc:creator>
		<pubDate>Mon, 26 Jun 2017 16:18:41 +0000</pubDate>
				<category><![CDATA[آموزش]]></category>
		<category><![CDATA[annotation]]></category>
		<category><![CDATA[Dagger]]></category>
		<guid isPermaLink="false">http://www.mahditajik.ir/?p=2398</guid>

					<description><![CDATA[<p>@Scope annotation اصولا هدف استفاده از این انوتیشن معرفی Scope آبجک تولید شده توسط Dagger2 است. یعنی Dagger2 به شما این امکان را می دهد تا Object های شما چرخه عمر متفاوت داشته باشند و شما فقط تعریف می کنید، پیاده سازی اش با خود Dagger است. فرض کنید که سه component به شرح زیر ...</p>
<p>نوشته <a rel="nofollow" href="http://www.mahditajik.ir/dagger2-custom-scopes/">برسی Scope@ ها در Dagger2</a> اولین بار در <a rel="nofollow" href="http://www.mahditajik.ir">Mahdi Tajik</a> پدیدار شد.</p>
]]></description>
										<content:encoded><![CDATA[<p><img decoding="async" loading="lazy" class="aligncenter size-full wp-image-2447" src="http://www.mahditajik.ir/wp-content/uploads/2017/07/dagger-scopes.jpg" alt="" width="800" height="486" srcset="http://www.mahditajik.ir/wp-content/uploads/2017/07/dagger-scopes.jpg 800w, http://www.mahditajik.ir/wp-content/uploads/2017/07/dagger-scopes-300x182.jpg 300w, http://www.mahditajik.ir/wp-content/uploads/2017/07/dagger-scopes-768x467.jpg 768w" sizes="(max-width: 800px) 100vw, 800px" /></p>
<p style="text-align: justify;"><span id="crayon-5957802600b1a924909351" class="crayon-syntax crayon-syntax-inline crayon-theme-classic crayon-theme-classic-inline crayon-font-monaco"><span class="crayon-pre crayon-code"><span class="crayon-n">@Scope</span> <span class="crayon-v">annotation</span></span></span></p>
<p style="text-align: justify;">اصولا هدف استفاده از این انوتیشن معرفی Scope آبجک تولید شده توسط <span class="highlight"><a href="http://www.mahditajik.ir/dagger2-advanced-example/" target="_blank" rel="noopener">Dagger2</a> </span>است. یعنی Dagger2 به شما این امکان را می دهد تا Object های شما چرخه عمر متفاوت داشته باشند و شما فقط تعریف می کنید، پیاده سازی اش با خود Dagger است. فرض کنید که سه component به شرح زیر داریم و سلسله مراتب ارتباط و وابستگی Component ها هم مشخص است.</p>
<p><img decoding="async" loading="lazy" class="aligncenter size-full wp-image-2388" src="http://www.mahditajik.ir/wp-content/uploads/2017/07/dagger-scopes.png" alt="" width="346" height="378" srcset="http://www.mahditajik.ir/wp-content/uploads/2017/07/dagger-scopes.png 346w, http://www.mahditajik.ir/wp-content/uploads/2017/07/dagger-scopes-275x300.png 275w" sizes="(max-width: 346px) 100vw, 346px" /></p>
<p>و ما برای آنها سه اسکوپ تعریف می کنیم. <strong>ActivityScope</strong>, <strong>UserScope</strong>, <strong>Applicationscope(singletone)</strong>.</p>
<p style="text-align: justify;"><strong>Dagger2</strong> به طور پیش فرض <strong>singletone</strong> یا همان <strong>applicationScope</strong> را دارد و چرخه عمرآن با چرخه عمر <strong>Application</strong> یکی است. احتمالاً در کد <strong>autogenerated</strong> خودش بصورت <strong>static</strong> نگهداری می کند. استفاده از این اسکوپ ها مانند این است که <strong>tag</strong> تعریف کنیم و اسمشان اهمیتی ندارد. فقط <strong>Object</strong> ای که با اسکوپ خاصی تولید می شود، طول عمر و <strong>LifeCycle</strong> اش با صدا زننده آن یکی خواهد شد. مثلا اگر یک <strong>Object</strong> با <strong>ActivityScope@</strong> داریم که در درون <strong>activity</strong> تزریق می شود، <strong>Lifecycle </strong> آن با <strong>Lifecycle</strong> مربوط به <strong>activity</strong> یکی می شود و تا زمانی وجود دارد که <strong>Activty</strong> تزریق کننده آن وجود داشته باشد و کنترل کردن آن اتوماتیک توسط <strong>Dagger2</strong> انجام می شود.</p>
<p style="text-align: justify;">به تصویر زیر توجه کنید:<img decoding="async" loading="lazy" class="aligncenter size-full wp-image-2389" src="http://www.mahditajik.ir/wp-content/uploads/2017/07/scopes-lifecycle.png" alt="" width="2226" height="1080" srcset="http://www.mahditajik.ir/wp-content/uploads/2017/07/scopes-lifecycle.png 2226w, http://www.mahditajik.ir/wp-content/uploads/2017/07/scopes-lifecycle-300x146.png 300w, http://www.mahditajik.ir/wp-content/uploads/2017/07/scopes-lifecycle-768x373.png 768w, http://www.mahditajik.ir/wp-content/uploads/2017/07/scopes-lifecycle-1024x497.png 1024w" sizes="(max-width: 2226px) 100vw, 2226px" /></p>
<p style="text-align: justify;"><strong>ApplicationScope</strong> در طول کل برنامه وجود دارد. پس ما برای هر آیتمی این اسکوپ را بگذاریم تا پایان برنامه وجود خواهد داشت. با شروع هر اکتیویتی، <strong>ActivityScope</strong> شروع و با بسته شدن آن اسکوپ هم تمام می شود. همچنین برای <strong>UserScope</strong>. با انتخاب یا ساخت هر یوزری شروع و  در نهایت با رهاکردن آن، تمام می شود.</p>
<p style="text-align: justify;">پس یادمان باشد که نام <strong>Scope</strong> ها مهم نیست. بلکه این مهم است که برای چه <strong>Provider</strong> ای تعریف شده و آن <strong>Object</strong> در چه کلاسی <strong>Inject</strong> می شود. برای ساخت آن بدین صورت عمل می کنیم:</p>
<pre class="crayon-plain-tag">@Scope
@Retention(RetentionPolicy.RUNTIME)
public @interface ScopeName{
}</pre>
منبع: <a href="http://www.biitecode.ir" target="_blank" rel="noopener">بایت کد</a></p>
<p>نوشته <a rel="nofollow" href="http://www.mahditajik.ir/dagger2-custom-scopes/">برسی Scope@ ها در Dagger2</a> اولین بار در <a rel="nofollow" href="http://www.mahditajik.ir">Mahdi Tajik</a> پدیدار شد.</p>
]]></content:encoded>
					
					<wfw:commentRss>http://www.mahditajik.ir/dagger2-custom-scopes/feed/</wfw:commentRss>
			<slash:comments>7</slash:comments>
		
		
			</item>
		<item>
		<title>Java Annotation چیست؟</title>
		<link>http://www.mahditajik.ir/java-annotation-%da%86%db%8c%d8%b3%d8%aa%d8%9f/</link>
					<comments>http://www.mahditajik.ir/java-annotation-%da%86%db%8c%d8%b3%d8%aa%d8%9f/#respond</comments>
		
		<dc:creator><![CDATA[mahdi]]></dc:creator>
		<pubDate>Mon, 01 Aug 2016 15:26:26 +0000</pubDate>
				<category><![CDATA[آموزش]]></category>
		<category><![CDATA[annotation]]></category>
		<category><![CDATA[IntDef]]></category>
		<category><![CDATA[java]]></category>
		<category><![CDATA[StringDef]]></category>
		<category><![CDATA[انوتیشن]]></category>
		<guid isPermaLink="false">http://www.mahditajik.ir/?p=1981</guid>

					<description><![CDATA[<p>, جاوا انوتیشن اطلاعات اضافی به کد ما اضافه می کند که بخشی از برنامه نیست ولی تاثیر در اجرای برنامه می گذارد. Annotations, a form of metadata, provide data about a program that is not part of the program itself. Annotations have no direct effect on the operation of the code they annotate. موضاعات ...</p>
<p>نوشته <a rel="nofollow" href="http://www.mahditajik.ir/java-annotation-%da%86%db%8c%d8%b3%d8%aa%d8%9f/">Java Annotation چیست؟</a> اولین بار در <a rel="nofollow" href="http://www.mahditajik.ir">Mahdi Tajik</a> پدیدار شد.</p>
]]></description>
										<content:encoded><![CDATA[<p><img decoding="async" loading="lazy" class="aligncenter size-full wp-image-1990" src="http://www.mahditajik.ir/wp-content/uploads/2016/07/annotitaion.jpg" alt="annotitaion" width="800" height="486" srcset="http://www.mahditajik.ir/wp-content/uploads/2016/07/annotitaion.jpg 800w, http://www.mahditajik.ir/wp-content/uploads/2016/07/annotitaion-300x182.jpg 300w, http://www.mahditajik.ir/wp-content/uploads/2016/07/annotitaion-768x467.jpg 768w" sizes="(max-width: 800px) 100vw, 800px" /></p>
<p>, جاوا انوتیشن اطلاعات اضافی به کد ما اضافه می کند که بخشی از برنامه نیست ولی تاثیر در اجرای برنامه می گذارد.</p>
<blockquote><p><a href="https://docs.oracle.com/javase/tutorial/java/annotations/" target="_blank" rel="noopener"><em>Annotations</em>, a form of metadata, provide data about a program that is not part of the program itself. Annotations have no direct effect on the operation of the code they annotate.</a></p></blockquote>
<p style="text-align: justify;">موضاعات مهمی که در انوتیشن مطرح است عبارتند از اطلاع رسانی به کامپایلر، انجام پردازش در زمان کامپایل و همچنین پردازش در زمان اجرا می باشد. انوتیشن ها توسط کامپایلر و یا ابزارهای تجزیه انوتیشن، تجزیه می شوند. قبل از این اطلاعات اضافی در javadoc قرار می گرفت، ولی توسط انوتیشن این اطلاعات را می توان در زمان کامپایل و حتی در زمان اجرا داشته باشیم. چند مثالی کاربردی خواهیم داشت و امیدوارم تا آخر این آموزش با من همراه باشید.</p>
<p style="text-align: justify;">انوتیشن های زیادی توسط خود زبان جاوا استفاده می شوند که شاید با خیلی از آنها همچون @Override آشنا باشید. علاوه بر انواع موجود می توان انوتیشن اختصاصی داشته باشیم که در مثال های بعدی با آنها مواجه خواهیم شد. توجه داشته باشید که انوتیشن می تواند ورودی داشته باشد یا اینکه نداشته باشد.</p>
<p style="text-align: justify;">چند نمونه:</p>
<p style="text-align: justify;"><b>@Override</b>  به کامپایلر می گوید که متد اظهار شده در کلاس اصلی را با دستوراتی ما بازنویسی کند.</p>
<p style="text-align: justify;"><b>@SuppressWarnings</b> می گوید که اخطارها را سرکوب کن. گرچه نمایش اخطار مفید است ممکن است در مواردی بخواهیم تا کامپایلر اخطاری را نمایش ندهد.</p>
<pre class="crayon-plain-tag">@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
}

@SuppressWarnings("unused")
public void unusedmethod(){

    //some methods
}

@SuppressWarnings("deprecation")
public void oldmethdthatDepricated(){

    //some methods
}</pre>
<p style="text-align: justify;">بعضی انوتیشن ها هم برای توصیف انوتیشن های دیگر بکار می رود. یعنی انوتیشن برای انوتیشن:</p>
<p style="text-align: justify;"><b>@Retention</b> می گوید که انوتیشن موردنظر چگونه ذخیره شود. استفاده است مثلا <code>RetentionPolicy.SOURCE</code>  انوتیشن اشاره شده در سطح سورس کدمی ماند و توسط کامپایلر قابل دسترسی نباشد. اگر مقدار را  <code>RetentionPolicy.CLASS </code> بگذاریم باعث می شود که انوتیشن مان در زمان کامپایل در نظر گرفته شود و توسط JVM ایگنور شود و یا توسط <code>RetentionPolicy.RUNTIME</code> انوتیشنمان توسط JVM نگهداری شود و در زمان اجرا قابل استفاده است.</p>
<p style="text-align: justify;"><b>@Documented</b> می گوید که انوتیشن بکار رفته باید توسط ابزار سندسازی جاوا به سند تبدیل شوند.</p>
<p style="text-align: justify;"><b>@Target</b>  توسط این انوتیشن، دسترسی المنت های جاوا به انوتیشن ما را محدود می کند و انواع انتخاب شده می توانند به انوتیشن ما دسترسی داشته باشند.</p>
<p style="text-align: justify;"><b>@Inherited</b> توجه کنید که انوتیشن ها ارث بری ندارند. یعنی مثلا اگر یک کلاسی با یک انوتیشن خاصی درست کردید و یک کلاس دیگر از آن مشتق شد اگر از این انوتیشن استفاده نکرده باشید کلاس جدید انوتیشن های پدر را به ارث نمی برد. در مثالی که بعد از تعاریف می زنم تمام این مطالب را نمایش خواهم داد.</p>
<p style="text-align: justify;"><b>@Repeatable</b>  این امکان در جاوای ۸ اضافه شده که می توانیم چند انوتیشن یکسان ولی با مقادیر مختلف را به یک متد اضافه کنیم. مثلاً در مثال زیر دوبار انوتیشن آلارم را با دو role متفاوت اعمال کردیم.</p>
<pre class="crayon-plain-tag">@Alert(role="Manager")
@Alert(role="Administrator")
public class UnauthorizedAccessException extends SecurityException { ... }</pre>
<p style="text-align: justify;">حال که با برخی انوتیشن های پیش فرض آشنا شدیم می خواهیم نحوه ساخت انوتیشن را باهم برسی کنیم. انوتیشن بسیار شبیه به اینترفیس ساخته می شود با این تفاوت که از کاراکتر @ استفاده می کنیم.</p>
<pre class="crayon-plain-tag">package com.example.mtajik.annotationtest;


import java.lang.annotation.*;

@Inherited
@Documented
@Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)

@interface BasicInformation {
    String corpId() default "mobiro";
    String corpAddress() default "kordestan .st";
}</pre>
<p style="text-align: justify;">انوتیشنی ساختیم که اطلاعات کلی کارمندان را نگهداری می کند. همانطور که ملاحظه می کنید انوتیشن می تواند متد داشته باشد. متد های آن می تواند مقدار پیش فرض داشته باشد. همچنین انوتیشن ما خودش چند انوتیشن دارد که در بالا تعریف کردیم. سپس کلاس کارمند با انوتیشن تولید شده را بصورت زیر می سازیم:</p>
<pre class="crayon-plain-tag">package com.example.mtajik.annotationtest;

@BasicInformation(corpId="Irancell", corpAddress="Vanak .ave")
public class Employee {
    String eId;
    String eName;
    public Employee(String eId, String eName){
        this.eId = eId;
        this.eName = eName;
    }

    public void getEmployeeDetails(){
        System.out.println("Employee ID: "+eId);
        System.out.println("Employee Name: "+eName);
    }
}</pre>
<p style="text-align: justify;">سپس کلاس زیر را بسازید و برنامه را اجرا کرده و نتیجه را در کنسول ببینید. همانطور که در اول اشاره کردم این کلاس همان ابزار تجزیه انوتیشن است که توسط reflection در هنگام Runtime انوتیشن های موجود در کلاس را گرفته و نتیجه را نمایش می دهد.</p>
<pre class="crayon-plain-tag">package com.example.mtajik.annotationtest;


import java.lang.annotation.Annotation;
public class TestCustomAnnotationBasicBenefits {
    public static void main(String[] args) throws Exception{
        Employee emp = new Employee("E-100", "user3320018");
        emp.getEmployeeDetails();
        Class reflectedClass = emp.getClass();

        Annotation informationAnn = reflectedClass.getAnnotation(BasicInformation.class);
        BasicInformation bBenefits = (BasicInformation)informationAnn;
        System.out.println("corporation ID: "+bBenefits.corpId());
        System.out.println("corporation address: "+bBenefits.corpAddress());
    }
}</pre>
<p style="text-align: justify;">ملاحظه کردید که چگونه می توان با استفاده از Annotation از Meta-data در هنگام Runtime دسترسی پیدا کرد و استفاده کرد.</p>
<p style="text-align: justify;">همچنین می توان با استفاده از انوتیشن نوع ورودی را برای یک تابع محدود کرد و با آن مانند enum برخورد کرد. هرچند به نظر شخصی بنده بسیار مفید تر از enum خواهد بود زیرا اطلاعاتی به همراه دارد که بسیار جای مانور دارد. به مثال زیر توجه کنید.</p>
<p style="text-align: justify;"><strong>IntDef</strong></p>
<p style="text-align: justify;">انوتیشنی است که توسط آن یک عنصر  integer را ارائه می دهد که در هنگام استفاده فقط می توانیم از مقادیر داده شده استفاده کنیم. ما یک انوتیشن داریم به عنوان روزهای هفته که انواع آن را از مقادیر static انتخاب کردیم. ( انواع آن روزهای هفته است)</p>
<pre class="crayon-plain-tag">static public final int SHANBE_ = 0;
static public final int YEK_SHANBE_ = 1;
static public final int DO_SHANBE = 2;
static public final int SE_SHANBE_ = 3;
static public final int CHAHR_SHANBE_ = 4;
static public final int PANJ_SHANBE_ = 5;
static public final int JOMHE_ = 6;</pre>
<pre class="crayon-plain-tag">@IntDef({SHANBE_, YEK_SHANBE_,DO_SHANBE,SE_SHANBE_,CHAHR_SHANBE_,PANJ_SHANBE_, JOMHE_})
@Retention(RetentionPolicy.SOURCE)
@Inherited
public @interface RozayeHafte {}</pre>
<p style="text-align: justify;">حال متدی برای محاسبه حقوق داریم که ورودی آن را از جنس این انوتیشن می گذاریم. حال هر جا که متد را صدا بزنید intellisense ide یعنی Android Studio به عوان ورودی پیش فرض همان روز ها را به ما پیشنهاد می دهد! جالب است نه؟ این همان کاری است که در هنگام انتخاب visibility در View خودش بطور پیش فرض GONE و Visible و Invisible را پیشنهاد می دهد و اگر سورس کد View را در SDK های زیر ۲۲ ببینید ملاحظه خواهید کرد که از همین روش برای مشخص کردن ورودی هایش استفاده کرده است.</p>
<p><img decoding="async" loading="lazy" class="aligncenter size-full wp-image-2022" src="http://www.mahditajik.ir/wp-content/uploads/2016/08/test.jpg" alt="test" width="782" height="622" srcset="http://www.mahditajik.ir/wp-content/uploads/2016/08/test.jpg 782w, http://www.mahditajik.ir/wp-content/uploads/2016/08/test-300x239.jpg 300w, http://www.mahditajik.ir/wp-content/uploads/2016/08/test-768x611.jpg 768w" sizes="(max-width: 782px) 100vw, 782px" /></p>
<p>&nbsp;</p>
<p>استفاده از <strong>StringDef</strong> هم بهمین صورت است با این تفاوت که انواع آن string هستند.</p>
<p>سورس کامل</p><pre class="crayon-plain-tag">public class MainActivity extends AppCompatActivity {
    
    static public final int SHANBE_ = 0;
    static public final int YEK_SHANBE_ = 1;
    static public final int DO_SHANBE = 2;
    static public final int SE_SHANBE_ = 3;
    static public final int CHAHR_SHANBE_ = 4;
    static public final int PANJ_SHANBE_ = 5;
    static public final int JOMHE_ = 6;

    static public final String GHAWY = "ghavi";
    static public final String ZAEEF = "zaeef";
    static public final String PIZORI = "pizoori";


    public void mohasebeheHoggogh(@RozayeHafte int day, @GhodratBadani String body) {

        switch (day) {
            case SHANBE_:
                Toast.makeText(MainActivity.this, body + " SHANBE_", Toast.LENGTH_SHORT).show();
                break;
            case YEK_SHANBE_:
                Toast.makeText(MainActivity.this, body + " YEK_SHANBE_", Toast.LENGTH_SHORT).show();
                break;
            case JOMHE_:
                Toast.makeText(MainActivity.this, body + " JOMHE_", Toast.LENGTH_SHORT).show();
                break;
        }

    }


    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        
        mohasebeheHoggogh(JOMHE_, GHAWY);
    }

    private enum RozhayeHafteType2 {
        SHANBE_,
        YEK_SHANBE_,
        JOMHE_

    }

    @IntDef({SHANBE_, YEK_SHANBE_, DO_SHANBE, SE_SHANBE_, CHAHR_SHANBE_, PANJ_SHANBE_, JOMHE_})
    @Retention(RetentionPolicy.SOURCE)
    @Inherited
    public @interface RozayeHafte {
    }


    @StringDef({GHAWY, ZAEEF, PIZORI})
    @Inherited
    @Retention(RetentionPolicy.SOURCE)
    public @interface GhodratBadani {
    }
}</pre><p>
منبع: <a href="http://www.biitecode.ir" target="_blank" rel="noopener">بایت کد</a></p>
<p>نوشته <a rel="nofollow" href="http://www.mahditajik.ir/java-annotation-%da%86%db%8c%d8%b3%d8%aa%d8%9f/">Java Annotation چیست؟</a> اولین بار در <a rel="nofollow" href="http://www.mahditajik.ir">Mahdi Tajik</a> پدیدار شد.</p>
]]></content:encoded>
					
					<wfw:commentRss>http://www.mahditajik.ir/java-annotation-%da%86%db%8c%d8%b3%d8%aa%d8%9f/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
	</channel>
</rss>
