一、和Active Scheduler 执行的区别:
a) Active Scheduler都在一个线程中执行,所有不用进行线程切换,不用进行加锁解锁;
b) Active Scheduler 的执行优先级不会导致内核的抢占调用,抢占要占用CPU中断;
c) 但Active Scheduler 执行是每个任务要尽可能小,要不然就会把整个消息循环阻塞,所以做一些异步操作线程更有优势;
二、RThread
a) 可以设置优先级;
b) 可以调用 Kill, Terminate, Panic 结束一个线程;在8.0以后不能再调用以上函数杀死其它线程;
c) 主线程被杀死,则整个进程结束;
三、利用线程做异步操作例子:
_LIT(KThreadName, "ExampleThread"); // Name of the new thread
TInt SynchronousTask(); // Example of a long-running synchronous function
class CAsyncTask : public CActive
{// Active object class to wrap a long synchronous task
public:
~CAsyncTask();
static CAsyncTask* NewLC();
// Asynchronous request function
void DoAsyncTask(TRequestStatus& aStatus);
protected: // From base class
virtual void DoCancel();
virtual void RunL();
virtual TInt RunError(TInt anError);
private:
CAsyncTask();
void ConstructL();
// Thread start function
static TInt ThreadEntryPoint(TAny* aParameters);
private:
TRequestStatus* iCaller; // Caller’s request status
RThread iThread; // Handle to created thread
};
CAsyncTask::CAsyncTask()
: CActive(EPriorityStandard) // Standard priority unless good reason
{// Add to the active scheduler
CActiveScheduler::Add(this);
}
// Two-phase construction code omitted for clarity
CAsyncTask::~CAsyncTask()
{// Cancel any outstanding request before cleanup
Cancel(); // Calls DoCancel()
// The following is called by DoCancel() or RunL()
// so is unnecessary here too
// iThread.Close(); // Closes the handle on the thread
}
void CAsyncTask::DoAsyncTask(TRequestStatus& aStatus)
{
if (IsActive())
{
TRequestStatus* status = &aStatus;
User::RequestComplete(status, KErrAlreadyExists);
return;
}
// Save the caller’s TRequestStatus to notify them later
iCaller = &aStatus;
// Create a new thread, passing the thread function and stack sizes
// No extra parameters are required in this example, so pass in NULL
TInt res = iThread.Create(KThreadName, ThreadEntryPoint,
KDefaultStackSize, NULL, NULL);
if (KErrNone!=res)
{// Complete the caller immediately
User::RequestComplete(iCaller, res);
}
else
{// Set active; resume new thread to make the synchronous call
// (Change the priority of the thread here if required)
// Set the caller and ourselves to KRequestPending
// so the active scheduler notifies on completion
*iCaller = KRequestPending;
iStatus = KRequestPending;
SetActive();
iThread.Logon(iStatus); // Request notification when thread dies
iThread.Resume(); // Start the thread
}
}
TInt CAsyncTask::ThreadEntryPoint(TAny* /*aParameters*/)
{// Perform a long synchronous task e.g. a lengthy calculation
TInt res = SynchronousTask();
// Task is complete so end this thread with returned error code
RThread().Kill(res);
return (KErrNone); // This value is discarded
}
void CAsyncTask::DoCancel()
{// Kill the thread and complete with KErrCancel
// ONLY if it is still running
TExitType threadExitType = iThread.ExitType();
if (EExitPending==threadExitType)
{// Thread is still running
iThread.LogonCancel();
iThread.Kill(KErrCancel);
iThread.Close();
// Complete the caller
User::RequestComplete(iCaller, KErrCancel);
}
}
void CAsyncTask::RunL()
{// Check in case thread is still running e.g. if Logon() failed
TExitType threadExitType = iThread.ExitType();
if (EExitPending==threadExitType) // Thread is still running, kill it
iThread.Kill(KErrNone);
// Complete the caller, passing iStatus value to RThread::Kill()
User::RequestComplete(iCaller, iStatus.Int());
iThread.Close(); // Close the thread handle, no need to LogonCancel()
}
TInt CAsyncTask::RunError(TInt anError)
{
if (iCaller)
{
User::RequestComplete(iCaller, anError);
}
return (KErrNone);
}
四、线程间数据传递
对于 8.0 之前的SDK和之后的有所有不同,具体见后面的学习日志;