在 iOS 中以编程方式将 SQLite 数据导出到 Excel

2023-11-27

在我的应用程序中,我使用 sqlite 作为后端(在本地存储数据)。 我能够将数据插入到我的表中。但是我想要做的是,想要以编程方式将所有 sqlite 数据导入到 excel 中。而且我不想为此应用程序使用服务器。一旦生成 excel 工作表,用户应该能够邮寄该表。 这在 iPhone 中可能吗: 请帮帮我。

以下是我将数据插入表的代码:

-(IBAction)Login
{
sqlite3_stmt *stmt;
        char *errorMsg; 
        char *update1 = "insert into Login1 values (?,?,?,?);";
        int x = sqlite3_prepare_v2(database, update1, -1, &stmt, nil);

    if (x == SQLITE_OK) 
    { 
        sqlite3_bind_text(stmt, 1, NULL,-1, NULL);
        sqlite3_bind_text(stmt, 2, [USERID UTF8String],-1, NULL);
        sqlite3_bind_text(stmt, 3, [str1 UTF8String],-1, NULL);
        sqlite3_bind_text(stmt, 4, [str4 UTF8String],-1, NULL);


    } 

    if (sqlite3_step(stmt) != SQLITE_DONE)
        NSLog(@"Error: %@",errorMsg); 
    sqlite3_finalize(stmt);

}


对于我执行此操作的应用程序,SQLite 数据相当大。因此,我使用后台线程将所有数据导出到 CSV(逗号分隔值)文件,Excel 可以导入该文件,然后打开邮件编辑器,并将 CSV 文件作为附件。如果您的数据很小,您可能不需要使用后台线程:

- (IBAction) export: (id) sender
{    
    // in my full code, I start a UIActivityIndicator spinning and show a 
    //  message that the app is "Exporting ..."

    [self performSelectorInBackground: @selector(exportImpl) withObject: nil];
}

Here is exportImpl

- (void) exportImpl
{
    NSAutoreleasePool* pool = [[NSAutoreleasePool alloc] init];

    NSArray* documentPaths = NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSSystemDomainMask, YES);
    NSString* documentsDir = [documentPaths objectAtIndex:0];
    NSString* csvPath = [documentsDir stringByAppendingPathComponent: @"export.csv"];

    // TODO: mutex lock?
    [sqliteDb exportCsv: csvPath];

    [pool release];

    // mail is graphical and must be run on UI thread
    [self performSelectorOnMainThread: @selector(mail:) withObject: csvPath waitUntilDone: NO];
}

- (void) mail: (NSString*) filePath
{
    // here I stop animating the UIActivityIndicator

    // http://howtomakeiphoneapps.com/home/2009/7/14/how-to-make-your-iphone-app-send-email-with-attachments.html
    BOOL success = NO;
    if ([MFMailComposeViewController canSendMail]) {
        // TODO: autorelease pool needed ?
        NSData* database = [NSData dataWithContentsOfFile: filePath];

        if (database != nil) {
            MFMailComposeViewController* picker = [[MFMailComposeViewController alloc] init];
            picker.mailComposeDelegate = self;
            [picker setSubject:[NSString stringWithFormat: @"%@ %@", [[UIDevice currentDevice] model], [filePath lastPathComponent]]];

            NSString* filename = [filePath lastPathComponent];
            [picker addAttachmentData: database mimeType:@"application/octet-stream" fileName: filename];
            NSString* emailBody = @"Attached is the SQLite data from my iOS device.";
            [picker setMessageBody:emailBody isHTML:YES];

            [self presentModalViewController:picker animated:YES];
            success = YES;
            [picker release];
        }
    }

    if (!success) {
        UIAlertView* warning = [[UIAlertView alloc] initWithTitle: @"Error"
                                                          message: @"Unable to send attachment!"
                                                         delegate: self
                                                cancelButtonTitle: @"Ok"
                                                otherButtonTitles: nil];
        [warning show];
        [warning release];
    }
}

然后,我有一个类封装了所有 SQLite 数据。该类是唯一进行 sqlite 调用的类。在本课程中,我有一种将数据导出到应用程序中的 CSV 文件的方法caches目录。变量sqliteDb上面的代码是这个类的一个实例。导出数据的方法如下:

-(void) exportCsv: (NSString*) filename
{
    // We record this filename, because the app deletes it on exit
    self.tempFile = filename;

    NSAutoreleasePool* pool = [[NSAutoreleasePool alloc] init];
    // Setup the database object
    sqlite3* database;

    // Open the database from the users filessytem
    if (sqlite3_open([self.databasePath UTF8String], &database) == SQLITE_OK)
    {
        [self createTempFile: filename];
        NSOutputStream* output = [[NSOutputStream alloc] initToFileAtPath: filename append: YES];
        [output open];
        if (![output hasSpaceAvailable]) {
            NSLog(@"No space available in %@", filename);
            // TODO: UIAlertView?
        } else {
            NSString* header = @"Source,Time,Latitude,Longitude,Accuracy\n";
            NSInteger result = [output write: [header UTF8String] maxLength: [header length]];
            if (result <= 0) {
                NSLog(@"exportCsv encountered error=%d from header write", result);
            }

            BOOL errorLogged = NO;
            NSString* sqlStatement = @"select timestamp,latitude,longitude,horizontalAccuracy from my_sqlite_table";

            // Setup the SQL Statement and compile it for faster access
            sqlite3_stmt* compiledStatement;
            if (sqlite3_prepare_v2(database, [sqlStatement UTF8String], -1, &compiledStatement, NULL) == SQLITE_OK)
            {
                 // Loop through the results and write them to the CSV file
                 while (sqlite3_step(compiledStatement) == SQLITE_ROW) {
                     // Read the data from the result row
                     NSInteger secondsSinceReferenceDate = (NSInteger)sqlite3_column_double(compiledStatement, 0);
                     float lat = (float)sqlite3_column_double(compiledStatement, 1);
                     float lon = (float)sqlite3_column_double(compiledStatement, 2);
                     float accuracy = (float)sqlite3_column_double(compiledStatement, 3);

                     if (lat != 0 && lon != 0) {
                         NSDate* timestamp = [[NSDate alloc] initWithTimeIntervalSinceReferenceDate: secondsSinceReferenceDate];
                         NSString* line = [[NSString alloc] initWithFormat: @"%@,%@,%f,%f,%d\n",
                                       table, [dateFormatter stringFromDate: timestamp], lat, lon, (NSInteger)accuracy];
                         result = [output write: [line UTF8String] maxLength: [line length]];
                         if (!errorLogged && (result <= 0)) {
                             NSLog(@"exportCsv write returned %d", result);
                             errorLogged = YES;
                         }
                         [line release];
                         [timestamp release];
                     }
                     // Release the compiled statement from memory
                     sqlite3_finalize(compiledStatement);
                 }
            }
        }
        [output close];
        [output release];
    }

    sqlite3_close(database);
    [pool release];
}

-(void) createTempFile: (NSString*) filename {
    NSFileManager* fileSystem = [NSFileManager defaultManager];
    [fileSystem removeItemAtPath: filename error: nil];

    NSMutableDictionary* attributes = [[NSMutableDictionary alloc] init];
    NSNumber* permission = [NSNumber numberWithLong: 0640];
    [attributes setObject: permission forKey: NSFilePosixPermissions];
    if (![fileSystem createFileAtPath: filename contents: nil attributes: attributes]) {
        NSLog(@"Unable to create temp file for exporting CSV.");
        // TODO: UIAlertView?
    }
    [attributes release];
}

我的代码正在导出位置信息的数据库。显然,里面exportCsv,您需要将我的 sqlite 调用替换为适合您的数据库内容的调用。

此外,代码将数据存储在临时文件中。您可能需要决定何时清除这些临时文件。

显然,这段代码是在 ARC 可用之前编写的。根据需要进行调整。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

在 iOS 中以编程方式将 SQLite 数据导出到 Excel 的相关文章

随机推荐

  • 攻击者可以有害地使用检查元素吗?

    我知道这是一个广泛的问题 但我认为我在这里遗漏了一些东西 攻击者是否可以通过简单地使用检查元素并编辑 javascript 和 html 来对站点造成损坏 例如 对于某人来说 更改输入的最大长度并上传太多数据可能会导致服务器崩溃 这似乎太容
  • C# 中的数组大小(长度)

    如何在 C 中确定数组的大小 长度 项目数 如果是一维数组a a Length 将给出的元素数量a If b是一个矩形多维数组 例如 int b new int 3 5 b Rank 将给出维数 2 和 b GetLength dimens
  • 多处理函数上的超时装饰器

    我有这个装饰器直接取自我在网上找到的一个例子 class TimedOutExc Exception pass def timeout timeout def decorate f def handler signum frame rais
  • 如何从 Azure DevOps 部署到 AWS Kubernetes

    我使用 Azure DevOps 来处理 PBI 存储库 PRS 和构建 但我的所有基础设施 包括 Kubernetes 均由 AWS 管理 没有文档 也没有关于如何使用 Azure DevOps 任务部署到 AWS EKS 的 正确且简单
  • 翻译动画的工作原理:Android

    我正在尝试移动一个RelativeLayout using TranslateAnimation 我为执行相同操作而编写的代码是 translateAnimation new TranslateAnimation 0 0 heightOfR
  • Spring HandlerInterceptors是如何实例化的?

    每个请求是否都有一个新的 Spring HandlerInterceptors 实例 我在 Spring 中有一个拦截器 它有一个类字段 public class MyInterceptor extends HandlerIntercept
  • 在 Cocoa KVO 中,为什么 NSMutableArray 代理上的更改不会通知观察者?

    我正在实施一个DocumentsManageriOS 中的类 我想创建一个名为的多对多属性documents符合 KVO 要求 它似乎大部分工作 并且我的 KVO 访问器和修改器方法被调用 然而 令我困扰的是 直接在NSMutableArr
  • 使用facet时ggplot2在面板边框之外

    我希望在多面图的外部有一个边框 但没有分隔图内面板的线 问题是 panel border 在构面中的每个面板周围绘制一个边框 而没有选择只在整个图周围有一个边框 或者 您可以将内部分隔线设置为 白色 但保持外部边框为 黑色 这是我的代码 m
  • Xcode 项目范围编译器标志

    使用 Xcode 4 2 和 LLVM 编译器 在针对 ARMv6 进行编译时 生成的应用程序中存在一些非常奇怪的错误 例如 CGSize 的 width 属性返回 height 为了解决这个问题 我发现我必须设置编译器标志 mno thu
  • 如何使用 requests 库发送 xml 正文?

    def request encoded xml urllib urlencode XML read xml encoded xml read xml headers Authorization AUTH TOKEN developerTok
  • 为什么应用太多参数会抛出“超出最大调用堆栈大小”?

    在 Chrome 和 Node 中 以下代码会引发错误 function noop var a new Array 1e6 Array 1000000 noop apply null a Uncaught RangeError Maximu
  • addActionListener 有什么作用?

    我有以下代码 JButton button new JButton Clear button addActionListener this 据我了解 我创建了一个按钮 上面写着 清除 然后我必须将一个动作与这个按钮关联起来 如果按下按钮会发
  • Python gc.get_count() 返回的 count0、count1 和 count2 值是什么

    python gc 包的文档对 gc get count 做了这样的描述 gc get count Return the current collection counts as a tuple of count0 count1 count
  • 在 Javascript 中使用引号和 innerHTML

    我编写了一些代码来让玩家了解故事的进展 当玩家单击按钮时 他们会看到一些新文本和更多选项 到目前为止一切顺利 但是当我传递带有附加参数的函数调用时 我需要单引号和双引号 但是 如果我同时使用两者 则会破坏innerHTML 代码如下 如果需
  • 如何获取JButton默认背景颜色?

    我用这个myButton setBackground myColor 改变JButton背景颜色为我的颜色 如何找到它原来的默认背景颜色 以便我可以将其更改回来 我知道我可以在更改和使用它之前保存它的默认背景颜色 但我想知道 Java 是否
  • 如何从 Json.NET 获取密钥列表?

    我正在使用 C 和 Json NET 如果我有一个 JObject 我想要对象内的键列表 类似于object Keys 返回对象内的键 这似乎是显而易见的 但我很难找到一种方法来做到这一点 Edit 我正在遍历该对象 并且我想在遍历时吐出对
  • 通过 Net:SSH 出现“非绝对主页”错误

    有问题的代码 Net SSH start server name user 这返回 非绝对家 用户 实际上有一个主目录 一种建议的方法是使用 IdentityFile 的完整路径修改 ssh config 这并没有解决问题 最疯狂的部分是
  • MATLAB:强制 doc 命令打开指定的参考 HTML 页面

    假设我在包中编写了一个类 名为mypackage myclass 我已经为包和类编写了自己的 HTML 文档 并将其包含在 MATLAB 帮助浏览器中 如下所述MATLAB 文档 我可以通过使用帮助浏览器直接导航到该 HTML 文档来显示该
  • 如何使用 Javascript 而不是 jQuery 用 JSON 数据动态填充 html 元素?

    我有以下 JSON 数据片段 items title sample 1 author author 1 title sample 2 author author 2 如何使用此数据填充以下 html 元素 div class news st
  • 在 iOS 中以编程方式将 SQLite 数据导出到 Excel

    在我的应用程序中 我使用 sqlite 作为后端 在本地存储数据 我能够将数据插入到我的表中 但是我想要做的是 想要以编程方式将所有 sqlite 数据导入到 excel 中 而且我不想为此应用程序使用服务器 一旦生成 excel 工作表