본문 바로가기
컴퓨터 공학/Android

[Do it 개정6판_안드로이드 스튜디오]둘째마당_11 단말에 데이터베이스와 내용 제공자 만들기

by hahehohoo 2019. 12. 3.
반응형

11-1 모바일 데이터베이스란?

- 데이터를 간단하게 저장하고 싶을 때는 SharedPreferences 를 사용, SQL 문

- 안드로이드는 Enbedded Database로 개발된 경량급 관계형 데이터베이스인 SQLite를 가지고 있다. 

 

11-2 데이터베이스와 테이블 만들기

- 간단한 방법으로는 Context 클래스에 정의된 openOnCreateDatabase() 메서드를 사용하는 것 

- 위 메서드의 첫 번째 파라미터는 '데이터베이스 이름' 두 번째 파라미터는 '사용 모드', 세 번째 파라미터는 Null이 아닌 객체를 지정할 경우 쿼리의 결과 값으로 반환되는 데이터를 참조하는 커서를 만들어낼 수 있다. 

 

>SampleDatabase 프로젝트

 

▼ MainActivity.java

package com.ogrg.techtown.sampledatabase;

import androidx.appcompat.app.AppCompatActivity;

import android.database.sqlite.SQLiteDatabase;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.TextView;

public class MainActivity extends AppCompatActivity {

    EditText editText;
    EditText editText2;
    TextView textView;
    String tableName;


    SQLiteDatabase database;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        editText = findViewById(R.id.editText);
        editText = findViewById(R.id.editText2);
        textView = findViewById(R.id.textView);

        Button button = findViewById(R.id.button);
        button.setOnClickListener(new View.OnClickListener(){

            @Override
            public void onClick(View v) {
                String databaseName = editText.getText().toString();
                createDatabase(databaseName);
            }
        });

        Button button2 = findViewById(R.id.button2);
        button2.setOnClickListener(new View.OnClickListener(){

            @Override
            public void onClick(View v) {
                tableName = editText2.getText().toString();
                createTable(tableName);

                insertRecord();
            }
        });
    }
    private void createDatabase(String name){
        println("createDatabase 호출됨");

        database = openOrCreateDatabase(name, MODE_PRIVATE, null);
        println("데이터베이스 생성함: " + name);
    }

    private void createTable(String name){
        println("createTable 호출됨");

        if(database == null){
            println("데이터베이스를 먼저 생성하세요.");
            return;
        }

        database.execSQL("create table if not exists " + name + "("
        + "_id integer PRIMARY KEY autoincrement, "//id를 자동으로 1씩 증가하는 킷값으로 정의함
                + "name text, "
                + "age integer,"
                + "mobile text)");

        println("데이브 생성함: " + name);

    }

    private void insertRecord() {
        println("insertRecord 메서드 호출되었습니다. ");
        if(database == null){
            println("데이터 베이스를 먼저 생성하세요. ");
            return;
        }

        if(tableName == null){
            println("데이터 베이스를 먼저 생성하세요. ");
            return;
        }

        database.execSQL("insert into " + tableName + "(name, age, mobile)" + "values " + "('John', 20, '010-10000-1000')");
        println("레코드 추가함");
    }

    public void println(String s){
        textView.append(s + "\n");
    }
}

- execSQL() 메서드는 SQL문을 파라미터로 전달받기 때문에 원하는 기능이 SQL을 먼저 정의해야 한다. 

- 테이블을 만들기 위ㅐ 칼럼을 직원 id, 이름, 나이, 휴대폰 번호로 정의

- id의 경우에는 안드로이드에 앞에 '_'를 붙여 '_id'로 만드는 방법을 권장함

- 테이블을 만들기 위한 SQL문은 "create table..."

- 레코드를 추가하는 SQL문은 결과 값을 받지 않으므로 "create table..." SQL 문과 "insert into ..."SQL문을 만들어 execSQL() 메서드로 실행 

 

칼럼(빨간)과 레코드(파란

 

 

11-3 헬퍼 클래스로 업그레이드 지원하기

- 테이블의 정의가 바뀌어서 스키마를 업그레이드할 필요가 있을 때에는 API에서 제공하는 헬퍼 클래스를 사용하는 것도 좋은 방법

- 헬퍼 클래스를 사용하려면 SQLiteOpenHelper 클래스를 사용해야 한다. 

 

>SampleDatabase2 프로젝트

 

▼ DatabaseHelper.java

package com.ogrg.techtown.sampledatabase;

import android.content.Context;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteOpenHelper;
import android.os.Build;
import android.util.Log;

public class DatabaseHelper extends SQLiteOpenHelper {
    public static String NAME = "employee.db";
    public static int VERSION = 1;

    public DatabaseHelper(Context context) {
        super(context, NAME, null, VERSION);
    }

    @Override
    public void onCreate(SQLiteDatabase db) {
        println("onCreate 호출됨");
        
        String sql = "Create table if not exists emp("
                + "id_ integer PRIMARY KEY autoincrement, "
                + "name text, "
                + "age integer, "
                + "mobile text)";
        db.execSQL(sql);
    }

    @Override
    public void onOpen(SQLiteDatabase db) {
        println("onCreate 호출됨");
    }
    
    @Override
    public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
        println("onUpgrade 호출됨: " + oldVersion + " -> "+ newVersion);
        
        if(newVersion > 1){
            db.execSQL("DROP TABLE IF EXISTS emp");
        }
    }
    public void println(String data) {
        Log.d("DatabaseHelper", data);
    }

    
}

 

▼ MainActivity.java

package com.ogrg.techtown.sampledatabase;

import androidx.appcompat.app.AppCompatActivity;

import android.database.sqlite.SQLiteDatabase;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.TextView;

public class MainActivity extends AppCompatActivity {

    EditText editText;
    EditText editText2;
    TextView textView;
    String tableName;

    DatabaseHelper dbHelper;
    SQLiteDatabase database;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        editText = findViewById(R.id.editText);
        editText2 = findViewById(R.id.editText2);
        textView = findViewById(R.id.textView);

        Button button = findViewById(R.id.button);
        button.setOnClickListener(new View.OnClickListener(){

            @Override
            public void onClick(View v) {
                String databaseName = editText.getText().toString();
                createDatabase(databaseName);
            }
        });

        Button button2 = findViewById(R.id.button2);
        button2.setOnClickListener(new View.OnClickListener(){

            @Override
            public void onClick(View v) {
                tableName = editText2.getText().toString();
                createTable(tableName);

                insertRecord();
            }
        });
    }
    private void createDatabase(String name){
        println("createDatabase 호출됨.");

        dbHelper = new DatabaseHelper(this);
        database = dbHelper.getWritableDatabase();

        println("데이터베이스 생성함: " + name);
    }

    private void createTable(String name){
        println("createTable 호출됨. ");

        if(database == null){
            println("데이터베이스를 먼저 생성하세요.");
            return;
        }

        database.execSQL("create table if not exists " + name + "("
                + "_id integer PRIMARY KEY autoincrement, "
                + "name text, "
                + "age integer,"
                + "mobile text)");

                println("테이블 생성함: " + name);
    }

    private void insertRecord() {
        println("insertRecord 메서드 호출되었습니다. ");
        if(database == null){
            println("데이터 베이스를 먼저 생성하세요. ");
            return;
        }

        if(tableName == null){
            println("데이터 베이스를 먼저 생성하세요. ");
            return;
        }

        database.execSQL("insert into " + tableName
                + "(name, age, mobile) "
                + "values "
                + "('John', 20, '010-10000-1000')");

        println("레코드 추가함");
    }

    public void println(String s){
        textView.append(s + "\n");
    }
}

- SQLiteDatabase 객체를 그대로 사용할 수 있으며 데이터베이스 버전이 변경되었을 때도 필요한 작업을 수행할 수 있는 구조가 만들어졌음

 

11-4 데이터 조회하기

>SampleDatabase2 프로젝트-2

▼ MainActivity.java

package com.ogrg.techtown.sampledatabase;

import androidx.appcompat.app.AppCompatActivity;

import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.TextView;

public class MainActivity extends AppCompatActivity {

    EditText editText;
    EditText editText2;
    TextView textView;
    String tableName;

    DatabaseHelper dbHelper;
    SQLiteDatabase database;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        editText = findViewById(R.id.editText);
        editText2 = findViewById(R.id.editText2);
        textView = findViewById(R.id.textView);

        Button button = findViewById(R.id.button);
        button.setOnClickListener(new View.OnClickListener(){

            @Override
            public void onClick(View v) {
                String databaseName = editText.getText().toString();
                createDatabase(databaseName);
            }
        });

        Button button2 = findViewById(R.id.button2);
        button2.setOnClickListener(new View.OnClickListener(){

            @Override
            public void onClick(View v) {
                tableName = editText2.getText().toString();
                createTable(tableName);

                insertRecord();
            }
        });

        Button button3 = findViewById(R.id.button3);
        button3.setOnClickListener(new View.OnClickListener(){

            @Override
            public void onClick(View v) {
                executeQuery();
            }
        });
    }

    public void executeQuery(){
        println("executaQuery 호출됨");

        Cursor cursor = database.rawQuery("select _id, name, age, moblie from emp", null);
        int recordCount = cursor.getCount();
        println("레코드 개수: " + recordCount);

        for(int i=0; i<recordCount; i++){
            cursor.moveToNext();
            int id = cursor.getInt(0);
            String name = cursor.getString(1);
            int age = cursor.getInt(2);
            String mobile = cursor.getString(3);

            println("레코드#" + i +":" + id + ", " + name + ", " + age + ", " + mobile);
        }
        cursor.close();
    }
    private void createDatabase(String name){
        println("createDatabase 호출됨.");

        dbHelper = new DatabaseHelper(this);
        database = dbHelper.getWritableDatabase();

        println("데이터베이스 생성함: " + name);
    }

    private void createTable(String name){
        println("createTable 호출됨. ");

        if(database == null){
            println("데이터베이스를 먼저 생성하세요.");
            return;
        }

        database.execSQL("create table if not exists " + name + "("
                + "_id integer PRIMARY KEY autoincrement, "
                + "name text, "
                + "age integer,"
                + "mobile text)");

                println("테이블 생성함: " + name);
    }

    private void insertRecord() {
        println("insertRecord 메서드 호출되었습니다. ");
        if(database == null){
            println("데이터 베이스를 먼저 생성하세요. ");
            return;
        }

        if(tableName == null){
            println("데이터 베이스를 먼저 생성하세요. ");
            return;
        }

        database.execSQL("insert into " + tableName
                + "(name, age, mobile) "
                + "values "
                + "('John', 20, '010-10000-1000')");

        println("레코드 추가함");
    }

    public void println(String s){
        textView.append(s + "\n");
    }
}

- Cursor 객체는 처음에는 아무런 레코드를 가리키지 않으며, moveToNext() 메서드를 이용해 그다음 레코드를 가리키도록 해야 레코드 값을 가져올 수 있어

- while 구문을 이용해  moveToNext() 가 false 값을 반환할 때까지 레코드 값을 가져오는 방법을 일반적으로 사용. 

- 커서는 데이터베이스와 마찬가지로 사용한 후에 close() 메서드를 이용해 닫아야 한다. 

 

 

 

소문난 명강의 오준석의 플러터 생존 코딩:Flutter와 Dart 입문부터 안드로이드와 iOS용 3가지 앱 개발까지, 한빛미디어이것이 자바다:신용권의 Java 프로그래밍 정복, 한빛미디어Hello Coding 프로그래밍:개념부터 처음 배우는, 한빛미디어처음 배우는 플러터:예제로 배우는 크로스 플랫폼 애플리케이션 개발, 한빛미디어돈 되는 안드로이드 앱 만들기:안드로이드 앱 개발을 위한 기본적이고 필수적인 내용 수록, 영진닷컴

 

 

반응형


댓글