জাভাতে কোনও টীকাটির মান পড়া কি সম্ভব?


102

এটি আমার কোড:

@Column(columnName="firstname")


private String firstName;

 @Column(columnName="lastname")
 private String lastName;

 public String getFirstName() {
  return firstName;
 }

 public void setFirstName(String firstName) {
  this.firstName = firstName;
 }

 public String getLastName() {
  return lastName;
 }

 public void setLastName(String lastName) {
  this.lastName = lastName;
 }

আমার টিকা @ কলামের কলাম ( কলামনাম = "xyz123") অন্য ক্লাসে পড়া কি সম্ভব ?

উত্তর:


123

হ্যাঁ, যদি আপনার কলাম টীকাটিতে রানটাইম ধরে রাখা থাকে

@Retention(RetentionPolicy.RUNTIME)
@interface Column {
    ....
}

আপনি এই মত কিছু করতে পারেন

for (Field f: MyClass.class.getFields()) {
   Column column = f.getAnnotation(Column.class);
   if (column != null)
       System.out.println(column.columnName());
}

আপডেট: ব্যক্তিগত ক্ষেত্রের ব্যবহার পেতে

Myclass.class.getDeclaredFields()

4
আমি আপনার সমাধান পছন্দ। আমরা কীভাবে এটি মাইক্লাসের পরিবর্তে টির মতো ব্যবহার করতে চাই তার মতো জেনেরিক তৈরি করতে পারি (ক্ষেত্র f: T.class.getFields ()) umn কলাম কলাম = f.getAnnotation (কলাম কলাম); if (কলাম! = নাল) System.out.println (কলাম। কলমনেম ()); }
এথার

4
হুবহু! আমি এটাও বের করার জন্য সংগ্রাম করে যাচ্ছি। যদি আমি কোনও টীকা প্রসেসর রাখতে চাই যা স্পষ্টভাবে কোনও শ্রেণীর নাম সরবরাহ করার প্রয়োজন হয় না? এটিকে প্রসঙ্গ থেকে বাছাই করা যায়; 'এই'??
5122014009

আমি নিশ্চিত নই যে আপনার দুজনের কী প্রয়োজন আমি তা বুঝতে পেরেছি। একটি সম্পূর্ণ উদাহরণ সহ একটি নতুন প্রশ্ন হিসাবে দয়া করে এটি জিজ্ঞাসা করুন। আপনি ইচ্ছে করলে এখানে লিঙ্ক করতে পারেন।
সেফালপড

4
Myclass.class.getDeclaredFields()ব্যক্তিগত ক্ষেত্রগুলি পেতে ব্যবহার করুন
q0re

এটা আমার জন্য কাজ করেছে। ধন্যবাদ আমি সুপারক্লাস বেসরকারী ক্ষেত্রের সন্ধান করছিলাম তাই আমি ক্লাসনাম.জেটসুপারক্লাস () ব্যবহার করতাম। getDeclaredFields ()
শশাঙ্ক

89

অবশ্যই এটা. এখানে একটি নমুনা টীকা:

@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public @interface TestAnnotation {

    String testText();
}

এবং একটি নমুনা টীকাযুক্ত পদ্ধতি:

class TestClass {

    @TestAnnotation(testText="zyx")
    public void doSomething() {}
}

এবং অন্য শ্রেণীর একটি নমুনা পদ্ধতি যা পরীক্ষার পাঠ্যটির মান মুদ্রণ করে:

Method[] methods = TestClass.class.getMethods();
for (Method m : methods) {
    if (m.isAnnotationPresent(TestAnnotation.class)) {
        TestAnnotation ta = m.getAnnotation(TestAnnotation.class);
        System.out.println(ta.testText());
    }
}

আপনার মত ফিল্ড টীকাগুলির জন্য খুব বেশি আলাদা নয়।

চিয়ার্জ!


22

আমি এটি কখনই করি নি, তবে দেখে মনে হচ্ছে প্রতিচ্ছবি এটি সরবরাহ করে। Fieldএটি একটি AnnotatedElementএবং তাই এটি আছে getAnnotationএই পৃষ্ঠার একটি উদাহরণ রয়েছে (নীচে অনুলিপি করা হয়েছে); বেশ সহজ সরল যদি আপনি টীকাটির ক্লাসটি জানেন এবং যদি টিকা নীতি রানটাইমে টীকাটি ধরে রাখে। স্বাভাবিকভাবে যদি ধরে রাখার নীতি রানটাইমে টীকা না রাখে, আপনি রানটাইমে এটিকে জিজ্ঞাসা করতে পারবেন না।

এর পরে মুছে ফেলা একটি উত্তর (?) একটি টীকা টিউটোরিয়ালের একটি দরকারী লিঙ্ক সরবরাহ করেছে যা আপনাকে সহায়ক মনে হতে পারে; আমি লিঙ্কটি এখানে অনুলিপি করেছি যাতে লোকেরা এটি ব্যবহার করতে পারে।

এই পৃষ্ঠা থেকে উদাহরণ :

import java.lang.annotation.Retention; 
import java.lang.annotation.RetentionPolicy;
import java.lang.reflect.Method;

@Retention(RetentionPolicy.RUNTIME)
@interface MyAnno {
  String str();

  int val();
}

class Meta {
  @MyAnno(str = "Two Parameters", val = 19)
  public static void myMeth(String str, int i) {
    Meta ob = new Meta();

    try {
      Class c = ob.getClass();

      Method m = c.getMethod("myMeth", String.class, int.class);

      MyAnno anno = m.getAnnotation(MyAnno.class);

      System.out.println(anno.str() + " " + anno.val());
    } catch (NoSuchMethodException exc) {
      System.out.println("Method Not Found.");
    }
  }

  public static void main(String args[]) {
    myMeth("test", 10);
  }
}

6

@ সেফালপোডের উত্তরের বিশদটি জানাচ্ছি, যদি আপনি একটি তালিকার সমস্ত কলামের নাম চান তবে আপনি এই অনেলাইনারটি ব্যবহার করতে পারেন:

List<String> columns = 
        Arrays.asList(MyClass.class.getFields())
              .stream()
              .filter(f -> f.getAnnotation(Column.class)!=null)
              .map(f -> f.getAnnotation(Column.class).columnName())
              .collect(Collectors.toList());

Objects.nonNull সম্পূর্ণরূপে গ্রহণ করার জন্য জাভা 8 :) .filter (চ -> nonNull (f.getAnnotation (Column.class)))
dehumanizer

4

যদিও এখন পর্যন্ত দেওয়া সমস্ত উত্তর পুরোপুরি বৈধ, তবে এন্টোটেশন স্ক্যানিংয়ের আরও সাধারণ এবং সহজ পদ্ধতির জন্য গুগল প্রতিচ্ছবি গ্রন্থাগারটিও মনে রাখা উচিত , যেমন

 Reflections reflections = new Reflections("my.project.prefix");

 Set<Field> ids = reflections.getFieldsAnnotatedWith(javax.persistence.Id.class);

3

আপনি জেনেরিক প্রকারগুলিও ব্যবহার করতে পারেন, আমার ক্ষেত্রে, যেমন কিছু করার আগে যা বলা হয়েছিল তা আমলে নিয়ে:

public class SomeTypeManager<T> {

    public SomeTypeManager(T someGeneric) {

        //That's how you can achieve all previously said, with generic types.
        Annotation[] an = someGeneric.getClass().getAnnotations();

    }

}

মনে রাখবেন যে এটি 100% সমক্লাস.ক্লাস.গেট (...) () এর সমান হবে না;

তবে কৌশলটি করতে পারেন ...


3

সাধারণ ক্ষেত্রে ক্ষেত্রগুলির জন্য আপনার ব্যক্তিগত অ্যাক্সেস রয়েছে, তাই আপনি প্রতিবিম্বে গেটফিল্ড ব্যবহার করতে পারবেন না। এর পরিবর্তে আপনার getDeclaredFields ব্যবহার করা উচিত

সুতরাং, প্রথমত, আপনার সচেতন হওয়া উচিত যদি আপনার কলাম টীকাটিতে রানটাইম ধরে রাখা থাকে:

@Retention(RetentionPolicy.RUNTIME)
@interface Column {
}

এর পরে আপনি এর মতো কিছু করতে পারেন:

for (Field f: MyClass.class.getDeclaredFields()) {
   Column column = f.getAnnotation(Column.class);
       // ...
}

স্পষ্টতই, আপনি ক্ষেত্রের সাথে কিছু করতে চান - টিকা মানটি ব্যবহার করে নতুন মান সেট করুন:

Column annotation = f.getAnnotation(Column.class);
if (annotation != null) {
    new PropertyDescriptor(f.getName(), Column.class).getWriteMethod().invoke(
        object,
        myCoolProcessing(
            annotation.value()
        )
    );
}

সুতরাং, সম্পূর্ণ কোডটি এর মতো দেখা যায়:

for (Field f : MyClass.class.getDeclaredFields()) {
    Column annotation = f.getAnnotation(Column.class);
    if (annotation != null)
        new PropertyDescriptor(f.getName(), Column.class).getWriteMethod().invoke(
                object,
                myCoolProcessing(
                        annotation.value()
                )
        );
}

2

কিছু সাধারণ জেনেরিক পদ্ধতি জিজ্ঞাসা করার জন্য, এটি আপনাকে সহায়তা করবে (5 বছর পরে: পি)।

আমার নীচের উদাহরণের জন্য, আমি অনুরোধম্যাপিং টিকা আছে এমন পদ্ধতিগুলি থেকে অনুরোধম্যাপিং ইউআরএল মানটি টানছি। ক্ষেত্রগুলির জন্য এটি মানিয়ে নিতে, কেবল পরিবর্তন করুন the

for (Method method: clazz.getMethods())

প্রতি

for (Field field: clazz.getFields())

আপনি যে টিকাটি পড়তে চাইছেন তার জন্য অনুরোধম্যাপিংয়ের ব্যবহারের স্বাপ করুন । তবে নিশ্চিত হয়ে নিন যে টীকাটি @ রিটেনশন (রিটেনশনপোলসি.আরুনটাইম) রয়েছে

public static String getRequestMappingUrl(final Class<?> clazz, final String methodName)
{
    // Only continue if the method name is not empty.
    if ((methodName != null) && (methodName.trim().length() > 0))
    {
        RequestMapping tmpRequestMapping;
        String[] tmpValues;

        // Loop over all methods in the class.
        for (Method method: clazz.getMethods())
        {
            // If the current method name matches the expected method name, then keep going.
            if (methodName.equalsIgnoreCase(method.getName()))
            {
                // Try to extract the RequestMapping annotation from the current method.
                tmpRequestMapping = method.getAnnotation(RequestMapping.class);

                // Only continue if the current method has the RequestMapping annotation.
                if (tmpRequestMapping != null)
                {
                    // Extract the values from the RequestMapping annotation.
                    tmpValues = tmpRequestMapping.value();

                    // Only continue if there are values.
                    if ((tmpValues != null) && (tmpValues.length > 0))
                    {
                        // Return the 1st value.
                        return tmpValues[0];
                    }
                }
            }
        }
    }

    // Since no value was returned, log it and return an empty string.
    logger.error("Failed to find RequestMapping annotation value for method: " + methodName);

    return "";
}

0

আমি এটি ব্যবহার করার একটি উপায়:

protected List<Field> getFieldsWithJsonView(Class sourceClass, Class jsonViewName){
    List<Field> fields = new ArrayList<>();
    for (Field field : sourceClass.getDeclaredFields()) {
        JsonView jsonViewAnnotation = field.getDeclaredAnnotation(JsonView.class);
        if(jsonViewAnnotation!=null){
            boolean jsonViewPresent = false;
            Class[] viewNames = jsonViewAnnotation.value();
            if(jsonViewName!=null && Arrays.asList(viewNames).contains(jsonViewName) ){
                fields.add(field);
            }
        }
    }
    return fields;
}    
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.