2016-01-26 87 views
2

我有一些我想要推廣的代碼。泛型的實現方法

我有一個泛型類

public class SynthesisFragmentAdapter<A extends Fragment & IBaseFragment, B extends Fragment & IBaseFragment> extends FragmentPagerAdapter { 

    private Context context; 

    private Class<A> synthesisFragmentClass1; 

    private Class<B> synthesisFragmentClass2; 

    public SynthesisFragmentAdapter(FragmentManager fm, Context context, 
              Class<A> synthesisFragmentClass1, 
              Class<B> synthesisFragmentClass2) { 
     super(fm); 
     this.context = context; 
     this.synthesisFragmentClass1 = synthesisFragmentClass1; 
     this.synthesisFragmentClass2= synthesisFragmentClass2; 
    } 

} 

我想調用這個類的時候,我需要動態地添加一個片段到SynthesisFragmentAdapter實例。我想這

// dynamically add same kind of fragment to adapter 
    protected void init(Class a, Class b , Fragment f1 , Fragment f2) { 

      TabLayout tab = (TabLayout) findViewById(R.id.tab); 

      ViewPager pager = (ViewPager) findViewById(R.id.pager); 

      SynthesisFragmentAdapter<f1 , f2> fragmentAdapter = new SynthesisFragmentAdapter<f1, f2>(getSupportFragmentManager(), this , a , b); 
      pager.setAdapter(fragmentAdapter); 
      tab.setupWithViewPager(pager); 
     } 

但我不認爲這是正確的,因爲我使用的片段實現除接口(IBaseFragment)延長Fragment。 我在做什麼錯?

+0

你有沒有編譯錯誤或運行時異常?程序是否按照你的意願去做? –

+0

@Erick G. Hagstrom。謝謝您的回覆 。事實上,我在SynthesisFragmentAdapter的實例化下遇到了一個編譯錯誤:「未知類f1,未知類f2」)。我想我錯過了一些東西,但我不知道爲什麼。 – ulquiorra

回答

2

請參閱方法init的聲明及其用法。

更新代碼:

public class MainActivity extends AppCompatActivity { 

protected <A extends Fragment & IBaseFragment, B extends Fragment & IBaseFragment> void init(Class<A> classA, Class<B> classB) { 
    TabLayout tab = (TabLayout) findViewById(R.id.tab); 
    ViewPager pager = (ViewPager) findViewById(R.id.pager); 
    SynthesisFragmentAdapter<A, B> fragmentAdapter = new SynthesisFragmentAdapter<>(getSupportFragmentManager(), this, classA, classB); 
    pager.setAdapter(fragmentAdapter); 
    tab.setupWithViewPager(pager); 
} 

@Override 
protected void onCreate(Bundle savedInstanceState) { 
    super.onCreate(savedInstanceState); 
    setContentView(R.layout.activity_main); 
    init(FragmentA.class, FragmentB.class); 
} 

interface IBaseFragment { 
} 


public static class FragmentA extends Fragment implements IBaseFragment { 
} 


public static class FragmentB extends Fragment implements IBaseFragment { 

} 

public class SynthesisFragmentAdapter<A extends Fragment & IBaseFragment, B extends Fragment & IBaseFragment> extends FragmentPagerAdapter { 


    private Context context; 

    private Class<A> synthesisFragmentClass1; 

    private Class<B> synthesisFragmentClass2; 

    public SynthesisFragmentAdapter(FragmentManager fm, Context context, 
            Class<A> synthesisFragmentClass1, 
            Class<B> synthesisFragmentClass2) { 
     super(fm); 
     this.context = context; 
     this.synthesisFragmentClass1 = synthesisFragmentClass1; 
     this.synthesisFragmentClass2 = synthesisFragmentClass2; 
    } 

    @Override 
    public int getCount() { 
     return 0; 
    } 

    @Override 
    public Fragment getItem(int position) { 
     return null; 
    } 
} 
+0

@ ErickG.Hagstrom更新了代碼 – gio

+1

有亞去!將類型參數放在'init()'方法上!好吧,我認爲你在這裏有一個勝利者。 –

+0

@gio它完美的作品。我從來沒有見過這樣的方法聲明。如果沒有你的幫助,我永遠無法找到它。我不知道該如何謝謝你。你救了我很多麻煩的人。非常感謝你 ! – ulquiorra

1

的問題是,該系統並不知道的f1f2在編譯時,也就是當它檢查類型參數的類型。類型參數在運行時被擦除,所以不能根據這些方法參數進行檢查。

如何更改您的SynthesisFragmentAdapter聲明?你真的需要類型參數中的extends表示法嗎?也許,你真正需要的是:

public class SynthesisFragmentAdapter extends FragmentPagerAdapter { 
    // ... 
    private Class<? extends Fragment> synthesisFragmentClass1; 
    private Class<? extends Fragment> synthesisFragmentClass2; 
    // etc. 

它只是看起來並不像你真的需要仿製藥這裏。

+0

非常感謝!最初我想做沒有泛型,因爲我有他們的一些麻煩,但它是我的規範規則強制:( – ulquiorra