Home PC Games Linux Windows Database Network Programming Server Mobile  
           
  Home \ Programming \ Dynamic programming Android     - OpenSSL for secure transmission and use of skills of files between Windows and Linux (Linux)

- MongoDB polymerization being given (Database)

- MySQL rollback insert statement causes ibd file grows double (Database)

- Ubuntu 15.04 installation Powercommands 2.0 (Linux)

- How to create SWAP files in Ubuntu 14.04 (Linux)

- MySQL use benchmarking tool sysbench (Database)

- RabbitMQ Getting Started Tutorial (Linux)

- Specifies the open ports of the SUSE firewall settings (Linux)

- Ubuntu deployment Flask + UWSGI + Nginx Comments (Server)

- Linux user groups, file permissions Detailed (Linux)

- Repair fatal error in Linux: lame / lame.h: No such file or dir Error (Linux)

- learning Linux ls command examples (Linux)

- What happens after the MySQL disk space is full (Database)

- Increase Linux system security --chattr (Linux)

- The Zabbix2.4.5 source compiler installation under Ubuntu 14.04 (Server)

- SQLite database commonly used sentences and visualization tools on MAC MeasSQLlite use (Database)

- Redis is installed in Ubuntu 14.04 (Database)

- Linux commands to access the cheat sheet (Linux)

- Inject script commands manually annotated summary (Linux)

- How to determine whether the Linux server was hacked (Linux)

 
         
  Dynamic programming Android
     
  Add Date : 2018-11-21      
         
         
         
  Note: This article is some example of the need for Java or Android have some programming foundation.

Compared with Python, Java is a more serious language. As a first learning Python programmer start Android will inevitably feel uncomfortable, somewhat rigid, very convenient way to miss the decorator and the like. In order to achieve a simple logic, you may need to write a lot of extra code.

For example, to do database queries, how to remove the instance of type User List from a Cursor to where?

Suppose this is the User

class User {
    int id;
    String name;
}

1. Locate the User corresponding to all columns and each column in the Cursor corresponding index.
2. If an index exists, remove the correct value depending on the type.
3. For each attribute, repeat the above procedure to remove the corresponding value.

{
  int columnIndex = cursor.getColumnIndex ( "id");
  if (columnIndex> = 0) {
    instance.id = cursor.getInt (columnIndex);
  }
}

{
  int columnIndex = cursor.getColumnIndex ( "name");
  if (columnIndex> = 0) {
    instance.name = cursor.getString (columnIndex);
  }
}
Do this problem?
* Repeat the code
* Repeat the code
* Bored
* Error-prone, poor maintenance

reflection

I just do not want to write so much boring code, how to do? Or try paradigm / reflection.
1. Remove all attributes.
2. cycle attributes of a queue.
3. set accessible properties.
4. Locate the index.
5. Remove the type of property, the correct value depending on the type taken from the Cursor inside.

public static T fromCursor (Cursor cursor, Class cls) {
    T instance = cls.newInstance ();
    List fields = Arrays.asList (cls.getDeclaredFields ())
    for (Field field: fields) {
      field.setAccessible (true);
      String fieldName = field.getName ();
      int columnIndex = cursor.getColumnIndex (fieldName);
      if (columnIndex <0) {
        continue;
      }
      Class fieldType = field.getType ();
      if (fieldType.equals (int.class)) {
        field.setInt (instance, cursor.getInt (columnIndex));
      } Else {
        // Handle more types String / float ...
   }
   return instance;
}
So we do not really boring to the same logic for each type of writing over and over again.

Processor

After using the reflection, there will be some other issues, such as code readability is not very good, not very easy to debug.

Now that we can achieve these through logical reflection, why not just reflected by this part of the code generated directly out of it?
1. Define your annotation to be processed.

@Retention (RetentionPolicy.CLASS)
@Target (ElementType.TYPE)
public @interface MyAnnotation {
  String value ();
}

2. Define your Processor classes, inheritance AbstractProcessor.

// Helper to define the Processor
@AutoService (Processor.class)
// Define the supported Java source code version
@SupportedSourceVersion (SourceVersion.RELEASE_7)
// Define which annotation you want to process
@SupportedAnnotationTypes ( "Com.glow.android.MyAnnotation")
public class MyProcessor extends AbstractProcessor {

3. The method overloading process, implement the logic of the generated code.

  @Override
  public boolean process (Set annotations, RoundEnvironment roundEnv) {
    Set elements = roundEnv.getElementsAnnotatedWith (MyAnnotation.class);
    Set typeElements = ElementFilter.typesIn (elements);
    for (TypeElement element: typeElements) {
      ClassName currentType = ClassName.get (element);
      MethodSpec.Builder builder = MethodSpec.methodBuilder ( "fromCursor")
       .returns (currentType)
       .addModifiers (Modifier.STATIC)
       .addModifiers (Modifier.PUBLIC)
       .addParameter (ClassName.get ( "android.database", "Cursor"), "cursor");

      ... // As reflected in that section, remove all of the fields, and remove each element cycle, that is, each column
      CodeBlock.Builder blockBuilder = CodeBlock.builder ();
      blockBuilder.beginControlFlow ( "");
      blockBuilder.addStatement ( "int columnIndex = cursor.getColumnIndex ($ S)", column);
      blockBuilder.beginControlFlow ( "if (columnIndex> = 0)");
      ColumnType columnType = columnTypeMap.get (column);
      String cursorType = null;
      if (columnType == ColumnType.INT) {
        cursorType = "Int";
      } Else if (columnType == ColumnType.LONG) {
        cursorType = "Long";
      } Else if (columnType == ColumnType.FLOAT) {
        cursorType = "Float";
      } Else if (columnType == ColumnType.STRING) {
        cursorType = "String";
      } Else {
        abort ( "Unsupported type", element);
      }

      blockBuilder.addStatement ( "instance. $ L = cursor.get $ L (columnIndex)",
            fieldName,
            cursorType);
      blockBuilder.endControlFlow ();
      blockBuilder.endControlFlow ();
      builder.addCode (blockBuilder.build ());
      // End loop

      // Generated code to a file
      String className = ... // set your code to be generated class name
      JavaFileObject sourceFile = processingEnv.getFiler () createSourceFile (className, element).;
      Writer writer = sourceFile.openWriter ();
      javaFile.writeTo (writer);
      writer.close ();
    }

    return false;
  }

4. Modify Userclass add annotation

@MyAnnotation
class User {
    int id;
    String name;
}

5. apt tool to write on our library to the compilation process to go.

Tips:
* Use AutoService can easily generate Processor Method
* Strong push Javapoet, beautiful code used to generate

AOP

AOP Processor practices and similar, not detailed here. You may use AspectJ.

Gradle plugin

Finally, I did not fully use the above method because:
* Code is generated at compile time when you open the compiler can not find
* Sometimes some special needs, such as the use of many attributes to be shared in multiple places, can be configured based would be better

So we use Gradle Plugin to generate code via the configuration file

The following is a simple example:
1. Define the configuration file, where the choice of a relatively simple document toml

srcDir = "src / main / java"
pkg = "com.glow.android.storage.db"
[[Tables]]
name = "user"
  [[Tables.columns]]
  name = "id"
  type = "int"
  isKey = true

2. Create a project in the Plugin in buildSrc

public class DbPlugin implements Plugin {

  @Override
  void apply (Project project) {
    project.task ( 'initDb') << {
      def dir = project.getProjectDir ()
      def file = new File (dir, "table.toml")
      generateCode (dir, new Toml (). parse (file) .to (DB.class))
    }
  }

  static void generateCode (File dir, DB db) {
    def outputDir = new File (dir, db.srcDir)
    outputDir.mkdirs ()
    for (Table table: db.tables) {
      // Process it
    }
  }
}

3. that generate code as in the previous section talked about, from the data source defined in the annotation into toml
4. In the project where the Plugin reference into, and executed
5. This can get pretty good code has been generated
     
         
         
         
  More:      
 
- Nmcli based network management command-line tool (Linux)
- Build Python3.4 + PyQt5.5.1 + Eric6.1.1 development platform under Mac OS X 10.11.1 (Server)
- Linux System Getting Started tutorial: Ubuntu desktop using the command line to change the system proxy settings (Linux)
- Python image processing library (PIL) to install and simple to use (Linux)
- Use $ BASH ENV variable to mention the right way under Linux (Linux)
- Ubuntu prompt / lack of boot space solutions (Linux)
- RM Environment Database RMAN Backup Strategy Formulation (Database)
- Encounter ORA-00600: internal error code, arguments: [4194] ORA-1552 (Database)
- Manually generate AWR reports (Database)
- MySQL stored procedures execute dynamic sql statement (Database)
- Fedora 19/20 and Debian Jessie / Sid users to install FFmpeg 2.3.2 (Linux)
- Python script file directory traversal examples (Programming)
- SSH without password (Linux)
- Close Pycharm spell check (Programming)
- Inject script commands manually annotated summary (Linux)
- How to set cache valid time in Apache (Server)
- Node.js simple interface server (Server)
- Linux System Getting Started Learning: complete installation on Debian or Ubuntu kernel source (Linux)
- Use pg_basebackup build PostgreSQL streaming replication environment (Database)
- Python programmers most often committed ten errors (Programming)
     
           
     
  CopyRight 2002-2020 newfreesoft.com, All Rights Reserved.