Basic Objective-C

 

IBOutlet
IBOutlet เป็นการประกาศให้ IB ( interface builder ) รับรู้ว่า ตัวแปรนี้ สามารถเชื่อมต่อเข้ากับ Object ใน nib , xib ได้ พูดอีกในทางหนึ่งได้ว่า IBOutlet จะเป็นตัวแทนของ Object ที่เราได้ออกแบบใน IB นั่นเอง

 

IBAction
เมื่อเราต้องการให้ Control ต่างๆใน interface builder สามารถตอบสนองต่อ action ได้ เราต้องประกาศ method ให้เป็น IBAction ยกตัวอย่างว่า ถ้าเราจะเขียนว่า กดปุ่มแล้วให้ไปเรียกใช้ method นี้ เราต้องประกาศใน method ให้เป็น IBAction โดยปกติแล้ว การประกาศ IBAction จะรับ parameter เป็น id

 

Delegate
คือ object ที่ทำหน้าที่เสมือนตัวแทนของ object อื่น เหมือนเวลาเราไปกินข้าวนอกบ้าน สมมติว่าเราอยากกินข้าวผัด เราก็อาจจะไปสั่งให้พ่อครัวทำให้เรา หรือเราก็สั่งข้าวผัดจากพนักงาน พนักงานก็จะไปบอกคนทำเก็บเงินว่าเราสั่งรายการอะไรไป และก็เดินไปบอกพ่อครัวอีกทีว่าให้ทำข้าวผัด สุดท้ายก็ได้ข้าวผัดมาเหมือนกัน เช่น

Obj A———————>Obj B

Obj A——Delegate—–>Obj B

ในการเขียน Program ด้วย Cocoa มีการใช้ delegate instance เป็นลักษณะของ Helper Object โดยจุดประสงค์หลักๆคืิอ เพื่อให้ class ที่ inherit ไปนั้นสามารถเพิ่มเติมและแก้ไขการตอบสนองต่อ event ได้ง่ายขึ้น ยกตัวอย่างเช่นว่า ในการ close window เมื่อ event เกิดขึ้น object ต่างๆที่อยู่บน window นั้นมีข้อจำกัดในการรับรู้ว่า ส่วนอื่นๆมีการเปลี่ยนแปลงหรือไม่

 

การเขียน Class
การเขียน class ในภาษา objc นั้นจะแบ่งออกเป็น สามส่วนหลักๆคือ

  1. interface
  2. implement
  3. program

interface
การประกาศ class นั้นจะเริ่มด้วย @interface แล้วก็ตามด้วยชื่อของ classname และสำหรับ :parentClassname นั้นก็เป็นส่วนที่บอกว่า class นี้สืบทอด (inheritance) มาจาก class ไหน ในส่วนของ data member นั้นจะประกาศภายในเครื่องหมาย { และ } ส่วน function จะทำการประกาศ ข้างนอก { } และปิดท้ายด้วย @end

 

Sending Message
สำหรับ ภาษา objective-c นั้นจะทำการเรียก function หรือว่า method ว่าเป็นการส่ง message ไปให้มัน ซึ่งรูปแบบก็คือ

[receiver message];

ซึ่งถ้าเทียบกับภาษา C/C++ ก็จะได้ประมาณว่า

receiver->message();

เหมือนเราต้องการจะให้ receiver นั้นทำอะไร เราก็ต้องบอกให้มันทำให้เรานั่นเอง

ขออธิบายในส่วนของ main program กันก่อนละกัน

Book *scibook;
scibook = [Book alloc];
[scibook init];

เราเริ่มประกาศตัวแปร scibook ให้เป็น pointer ของ Book และทำการส่ง message ที่ชื่อว่า alloc ไปให้ Book เพื่อทำการจอง memory แล้วหลังจากการจองแล้ว ก็ยังไม่สามารถใช้ได้เลย ต้องทำการ initialize มันซะก่อน ด้วยการส่ง message บอกให้ init อีกที

ปล. initialize คือการให้ค่าเริ่มต้นสำหรับตัวแปรต่างๆ เพราะว่าในการจอง memory นั้น พื้นที่ที่โดนจองอาจจะมีค่าต่างๆที่หลงเหลือจากโปรแกรม อื่นๆ เราก็ต้องปัดกวาด พื้นที่ตรงนั้นให้มันพร้อม เสียก่อน

สำหรับ บรรทัดต่อมา เป็นการรวมสองบรรทัดเข้าด้วยกันเลย ก็จะได้ว่า

Book *mathbook = [[Book alloc] init];

เมื่อเรามี object แล้วก็สามารถเรียกใช้ function โดยการส่ง message ไปให้ object เช่น

[mathbook setID: 1];

 

Inheritance (การสืบทอด)
สำหรับหัวข้อนี้จะกล่าวถึงรายละเอียดต่างๆเกี่ยวกับ Inheritance (การสืบทอด) ว่ามันคืออะไรและมีความสำคัญยังไง ตั้งแต่พื้นๆก่อนเลยละกัน ก่อนอื่นมาทำความเข้าใจ ของความหมาย ของคำว่า

Root class
ความหมายของ root คือ class ที่ไม่มี parent หรือหมายความง่ายๆว่ามันไม่ได้ไปสืบทอดใคร
Parent class
ส่วน parent นั้นก็คือ class ที่เป็นต้นแบบของ class อื่นๆ และตัว parent เองก็อาจจะสืบทอดคนอื่น(child) มาอีกทีก็ได้
Child class
เป็นการเรียก class ที่สืบทอดมาจากคนอื่น
เพื่อความเข้าใจง่ายๆ ยกตัวอย่าง เรื่องของสัตว์มาประกอบ ก็แล้วกันน่ะสัตว์ทั้งหมดในโลก ขอเรียกว่า เป็น Animal ทั้งหมดเลยแล้วกัน แล้วสัตว์ต่างๆ ก็อาจจะแบ่งออกได้เป็น Mammal ( สัตว์เลี้ยงลูกด้วยนม ) และ Fish ( ปลา ) และ ถ้าในบรรดาเหล่า Mammal ก็มี Dog ซึ่งเป็นสัตว์ชนิดหนึ่งเหมือนกัน
เพื่อความเข้าใจง่ายๆ ดูภาพประกอบ

อธิบายตามภาพ

Animal เป็น Root Class
คลาสที่ต่อออกมาจาก animal ก็คือ mammal ( สัตว์เลี้ยงลูกด้วยนม ) ดังนั้น parent class ของ mammal ก็คือ Animal
Fish เป็น class ที่สืบทอดมากจา animal พูดง่ายๆว่าเป็น child ของ animal และก็แน่นอนว่า Fish มี parent class คือ animal เช่นเดียวกัน
และสุดท้าย mammal มี child class ที่ชื่อว่า dog และในทางกลับกัน dog ก็จะมี parent class เป็น Mammal
ถ้าหากเราให้คุณสมบัติของ class ต่างๆ เช่นว่า

animal เป็นสิ่งมีชีวิตที่ต้องกินอาหาร
mammal เลี้ยงลูกด้วยนม
fish หายใจในน้ำได้

นั่นก็แปลได้ว่า dog นั้นเป็นสิ่งมีชีวิตที่ต้องกินอาหาร ( สืบทอดจาก animal ) และเป็นสัตว์เลี้ยงลูกด้วยนม ( สืบทอดจาก mammal ) แต่ไม่อาจจะหายใจในน้ำได้เพราะไม่ได้สืบทอดมาจาก Fish

เราลองมาเขียน class จากแผนภาพในแบบง่ายๆกัน

// animal class
@interface Animal
{
string name;
}
– (void) eat;

จาก code ข้างบน ประกาศ class ชื่อว่า animal โดยมี ตัวแปรเป็น string เอาไว้เก็บชื่อของสัตว์ตัวนี้ และสัตว์ต่างๆก็ต้องการ การกินอาหาร เลยประกาศ method ชื่อว่า eat ขึ้นมา

// Mammal.h
@interface Mammal :Animal
{
int blood_temperature;
}
– (void) feedMilk;

แล้วก็ประกาศ class ชื่อว่า mammal ขึ้นมา โดยสืบทอดมาจาก animal และก็เพิ่ม method ชื่อว่า feedMilk เข้าไป จากตรงนี้ Mammal ก็จะสามารถเรียกใช้ method ของ animal ได้ด้วย นั่นก็คือ eat นั่นเอง และส่วนตัวของ mammal เองก็มี method ของตัวเองที่ชื่อ feedMilk ด้วย

// dog.h
@interface Dog :Mammal
{
}
– (void) bite;
– (void) run;

สุดท้ายที่เราประกาศก็คือ dog โดยเพิ่ม method เข้ามาอีกสองอันนั่นก็คือ bite กับ run

สรุปได้ว่า ตอนนี้ dog นั้นสามารถ eat , feedMilk , bite , run ทำได้ทั้ง 4 อย่างเลย
จะเห็นได้ว่า inheritance นั้นมีประโยชน์มาก เพราะว่าเราสามารถ สร้าง class ใหม่ขึ้นมาได้ จาก class ที่มีอยู่แล้ว ทำให้เราลดเวลาการเขียนโปรแกรมลงได้ได้เยอะมาก และเป็นส่วนสำคัญสำหรับ การเขียนโปรแกรมในแบบ OOP ( Object Oriented Programming )

 

Polymorphisms
Polymorphisms สรุปง่ายๆว่าเป็นการอนุญาติให้ derived class ( child class ) สามารถใช้ function ของ parent ได้ สำหรับ polymorphisms นั้นเห็นเด่นชัดมากที่สุดก็คงจะเป็น Overriding / Overloading

Overriding
เป็นการเขียน function ของ Child class ใช้เองโดยไม่ต้องใช้ function ของ Parent Class ถ้าจะยกตัวอย่างง่ายๆ ก็เป็นต้นว่า ถ้าเรามี class ชื่อว่า Car แล้ว Car นั้นมีฟังชั่นขื่อว่า drive สมมติว่าเราจะเขียน class ใหม่ขึ้นมาโดยสืบทอด (inherit) มาจาก Car โดยชื่อว่า Tank มีฟังชั่นชื่อว่า drive เหมือนกัน แต่ว่า class ทั้งสองนั้น Drive ทำงานไม่เหมือนกัน คือพูดง่ายๆว่า รถยนต์ก็ ขับ(drive)ได้ รถถังก็ ขับ(drive) ได้ แต่วิธีการที่จะขับไม่เหมือนกัน
Overloading
เป็นการเขียน Function ชื่อเหมือนกัน ใน class เดียวกัน แต่รับ parameter คนละอย่างกัน เช่นว่า เรามี class ชื่อว่า Rectangle และมี function ในการคำนวนพื้นที่ เราอาจจะต้องการให้มันรับ parameter ได้ทั้ง int และ float ในลักษณะแบบนี้เราก็จะใช้ overloading เข้ามาให้เกิดประโยชน์
อาจจะงง เล็กน้อย สรุปสั้น Overriding ก็คือ child class ที่มีการเขียน function ที่ชื่อเหมือนกับ parent ขึ้นมาเองโดยไม่ต้องสืบทอดจาก parent และ Overloading คือ method ที่สามารถรับ parameter ได้หลายๆรูปแบบ

อ่าน Polymorphisms เพิ่มเติมได้จาก macfeteria/Polymorphisms

 

Dynamic Binding
คือการเพิ่มความสามารถให้ Class หนึงให้มีความสามารถ(Method)เหมือนกัยอีก Class

อ่าน Dynamic Binding เพิ่มเติมได้จาก macfeteria/Dynamic Binding

 

Super Self – Initializing
super เป็น keyword ที่เอาไว้อ้างอิงถึง คลาสที่สืบทอดมา
self ก็คือเป็นการอ้างอิงถึงตัวเอง
เอาละทีนี้ก็คือว่า มันมีความสำคัญอะไรกับ 2 สิ่งนี้ สำหรับ self กับ super
จริงๆแล้ว self กับ super ส่วนมากจะได้ใช้จริงๆ กับ initial ซะส่วนมาก คือหลังจากการ alloc แล้วเราต้องทำการ init ให้มัน ทีนี้มันก็เกิดปัญหาที่ว่า ถ้าที่เราเขียน class ที่เป็น child จาก parent ที่ต้องการ initial ก่อนใช้งาน แล้วจะทำอย่างไร ?

อ่าน Super Self – Initializing เพิ่มเติมได้จาก macfeteria/Super Self – Initializing

ที่มา: macfeteria

Doc Comment syntax

Functions:
/**
* Does something interesting
* @access  Access level is already known from the “public”, “private”, or “protected”
* @param  Place    $where  Where something interesting takes place
* @param  integer  $repeat How many times something interesting should happen
* @throws Some_Exception_Class If something interesting cannot happen
* @return Status
*/
Classes:
/**
* Short description for class
*
* Long description for class (if any)…
*
* @copyright  2006 Zend Technologies
* @license    http://www.zend.com/license/3_0.txt   PHP License 3.0
* @version    Release: @package_version@
* @link       http://dev.zend.com/package/PackageName
* @since      Class available since Release 1.2.0
*/

mongorestore with password

zDev:~ mac$ mongorestore -u user -p pssword -d my_db path/to/bson 
connected to: 127.0.0.1
Thu Jun 28 18:46:26 /Users/path/to/bson/groups.bson
Thu Jun 28 18:46:26 going into namespace [my_db.groups]
2 objects found

Thu Jun 28 18:46:26 /Users/path/to/bson/users.bson
Thu Jun 28 18:46:26 going into namespace [my_db.users]
1 objects found

Thu Jun 28 18:46:26 /Users/path/to/bson/system.indexes.bson
Thu Jun 28 18:46:26 going into namespace [my_db.system.indexes]
Thu Jun 28 18:46:26 { name: “_id_”, ns: “my_db.groups”, key: { _id: 1 } }
Thu Jun 28 18:46:26 { name: “_id_”, ns: “my_db.users”, key: { _id: 1 } }
2 objects found

RESTful testing with cURL

POST data to a REST resource:
curl -i -H "Accept: application/json" -X POST -d "firstName=james" http://resturl/section/sub

where,
i – show response headers
H – pass request headers to the resource
X – pass a HTTP method name
d – pass in parameters enclosed in quotes; multiple parameters are separated by ‘&’
The above command posts the first name “james” to the persons resource. Assuming the server creates a new person resource with first name of James, I also tell the server to return a json representation of the newly created resource.

 

PUT a resource:
curl -i -H "Accept: application/json" -X PUT -d "phone=1-800-999-9999" http://resturl/persons/person/1

This puts a phone number to the person resource created in the previous example.

 

GET a resource:
curl -i -H "Accept: application/json" http://resturl/persons/person/1

For GET requests, the -X GET option is optional.

curl -i -H "Accept: application/json" http://resturl/persons?zipcode=93031

You can pass in query parameters by appending it to the url.

curl -i -H "Accept: application/json" "http://resturl/persons?firstName=james&lastName=wallis"
The resource uri needs to be quoted if you pass in multiple query parameters separated by ‘&’. If you have spaces in the query values, you should encode them i.e. either use the ‘+’ symbol or %20 instead of the space.

 

DELETE a resource:

curl -i -H "Accept: application/json" -X DELETE http://resturl/persons/person/1
To delete a resource, supply DELETE as a -X option.

Using POST to PUT a resource:

curl -i -H "Accept: application/json" -H "X-HTTP-Method-Override: PUT" -X POST -d "phone=1-800-999-9999" http://resturl/persons/person/1

Some clients do not support PUT or it’s difficult to send in a PUT request. For these cases, you could POST the request with a request header of X-HTTP-Method-Override set to PUT. What this tells the server is that the intended request is a PUT.
Most web servers (or you could code it) support the X-HTTP-Method-Override and convert the request method to the intended HTTP method (value of the X-HTTP-Method-Override)
This example puts a phone number (by POSTing) to the person resource identified by 1.

 

Using POST to DELETE a resource:

curl -i -H "Accept: application/json" -H "X-HTTP-Method-Override: DELETE" -X POST http://resturl/persons/person/1

Similar to the previous command, this example deletes the person resource identified by the above uri using the POST HTTP method but telling the server to override it with DELETE.

 

เพิ่มเติม REST-esting with cURL: File Handling

ที่มา REST-esting with cURL

IOS String Format Specifiers

Table 1  Format specifiers supported by the NSString formatting methods and CFString formatting functions
Specifier Description
%@ Objective-C object, printed as the string returned by descriptionWithLocale: if available, or description otherwise. Also works with CFTypeRef objects, returning the result of the CFCopyDescription function.
%% '%' character
%d%D,%i Signed 32-bit integer (int)
%u%U Unsigned 32-bit integer (unsigned int)
%hi Signed 16-bit integer (short)
%hu Unsigned 16-bit integer (unsigned short)
%qi Signed 64-bit integer (long long)
%qu Unsigned 64-bit integer (unsigned long long)
%x Unsigned 32-bit integer (unsigned int), printed in hexadecimal using the digits 0–9 and lowercase a–f
%X Unsigned 32-bit integer (unsigned int), printed in hexadecimal using the digits 0–9 and uppercase A–F
%qx Unsigned 64-bit integer (unsigned long long), printed in hexadecimal using the digits 0–9 and lowercase a–f
%qX Unsigned 64-bit integer (unsigned long long), printed in hexadecimal using the digits 0–9 and uppercase A–F
%o%O Unsigned 32-bit integer (unsigned int), printed in octal
%f 64-bit floating-point number (double)
%e 64-bit floating-point number (double), printed in scientific notation using a lowercase e to introduce the exponent
%E 64-bit floating-point number (double), printed in scientific notation using an uppercase E to introduce the exponent
%g 64-bit floating-point number (double), printed in the style of %e if the exponent is less than –4 or greater than or equal to the precision, in the style of %f otherwise
%G 64-bit floating-point number (double), printed in the style of %E if the exponent is less than –4 or greater than or equal to the precision, in the style of %f otherwise
%c 8-bit unsigned character (unsigned char), printed by NSLog() as an ASCII character, or, if not an ASCII character, in the octal format \ddd or the Unicode hexadecimal format \udddd, where d is a digit
%C 16-bit Unicode character (unichar), printed by NSLog() as an ASCII character, or, if not an ASCII character, in the octal format \ddd or the Unicode hexadecimal format \udddd, where d is a digit
%s Null-terminated array of 8-bit unsigned characters. %s interprets its input in the system encoding rather than, for example, UTF-8.
%S Null-terminated array of 16-bit Unicode characters
%p Void pointer (void *), printed in hexadecimal with the digits 0–9 and lowercase a–f, with a leading 0x
%L Length modifier specifying that a following aAeEfFg, or G conversion specifier applies to a long double argument
%a 64-bit floating-point number (double), printed in scientific notation with a leading 0x and one hexadecimal digit before the decimal point using a lowercase p to introduce the exponent
%A 64-bit floating-point number (double), printed in scientific notation with a leading 0X and one hexadecimal digit before the decimal point using a uppercase P to introduce the exponent
%F 64-bit floating-point number (double), printed in decimal notation
%z Length modifier specifying that a following dioux, or X conversion specifier applies to a size_t or the corresponding signed integer type argument
%t Length modifier specifying that a following dioux, or X conversion specifier applies to a ptrdiff_t or the corresponding unsigned integer type argument
%j Length modifier specifying that a following dioux, or X conversion specifier applies to a intmax_t or uintmax_t argument

Platform Dependencies

Mac OS X uses several data types—NSIntegerNSUInteger,CGFloat, and CFIndex—to provide a consistent means of representing values in 32- and 64-bit environments. In a 32-bit environment, NSInteger and NSUInteger are defined as int and unsigned int, respectively. In 64-bit environments, NSInteger and NSUInteger are defined as longand unsigned long, respectively. To avoid the need to use different printf-style type specifiers depending on the platform, you can use the specifiers shown in Table 2. Note that in some cases you may have to cast the value.

Table 2  Format specifiers for data types
Type Format specifier Considerations
NSInteger %ld or %lx Cast the value to long
NSUInteger %lu or %lx Cast the value to unsigned long
CGFloat %f or %g %f works for floats and doubles when formatting; but see below warning when scanning
CFIndex %ld or %lx The same as NSInteger
pointer %p %p adds 0x to the beginning of the output. If you don’t want that, use %lx and cast to long.
long long %lld or %llx long long is 64-bit on both 32- and 64-bit platforms
unsigned long long %llu or %llx unsigned long long is 64-bit on both 32- and 64-bit platforms

The following example illustrates the use of %ld to format an NSInteger and the use of a cast.

NSInteger i = 42;
printf("%ldn", (long)i);

In addition to the considerations mentioned in Table 2, there is one extra case with scanning: you must distinguish the types for float and double. You should use %f for float,%lf for double. If you need to use scanf (or a variant thereof) with CGFloat, switch to double instead, and copy the double to CGFloat.

CGFloat imageWidth;
double tmp;
sscanf (str, "%lf", &tmp);
imageWidth = tmp;

It is important to remember that %lf does not represent CGFloat correctly on either 32- or 64-bit platforms. This is unlike %ld, which works for long in all cases.

ที่มา: http://developer.apple.com/library/ios/#documentation/Cocoa/Conceptual/Strings/Articles/formatSpecifiers.html

Check Query String

$(document).ready(function() {
if(document.location.search == "?msg=thanks") {
$("#alert").html("Thanks for your submission!");
} else if(document.location.search == "?msg=error") {
$("#alert").html("There was an error with your submission!");
} else {

}
});