Взаимно блокируемый раньше увеличивал/имитировал булевскую переменную, действительно ли это безопасно?

В случае, если кто-то хочет использовать Ghostscript.NET .

Ghostscript.NET - (записанный в C#) является наиболее завершенной библиотекой управляемой оболочки вокруг библиотеки Ghostscript (32-разрядный & 64-разрядный), интерпретатор для языка PostScript, PDF.

Это зависит от исполняемого файла, который необходимо установить на машине. Вот ссылка от того, где Вы видите и загружаете последнюю версию exe.

https://www.ghostscript.com/download/gsdnld.html

P.S. Я испытал некоторые затруднения из-за последней версии 9.50, не бывшей способной считать страницы.

я предпочитаю использовать 9,26 версий.

https://github.com/ArtifexSoftware/ghostpdl-downloads/releases/download/gs926/gs926aw32.exe

https://github.com/ArtifexSoftware/ghostpdl-downloads/releases/download/gs926/gs926aw64.exe

Следующий шаг к [1 120], находят и устанавливают Ghostscript.NET от Nuget. Я загружаю PDF с URL CDN и использую MemoryStream, чтобы открыть и обработать файл PDF. Вот пример кода:

using (WebClient myWebClient = new WebClient())
            {
                using (GhostscriptRasterizer rasterizer = new GhostscriptRasterizer())
                {
                    /* custom switches can be added before the file is opened

                    rasterizer.CustomSwitches.Add("-dPrinted");

                    */
                    byte[] buffer = myWebClient.DownloadData(pdfUrl);
                    using (var ms = new MemoryStream(buffer))
                    {
                        rasterizer.Open(ms);
                        var image = rasterizer.GetPage(0, 0, 1);

                        var imageURL = "MyCDNpath/Images/" + filename + ".png";
                        _ = UploadFileToS3(image, imageURL);
                    }
                }
            }

можно также использовать его с временным FileStream. Вот другой пример. Обратите внимание, что Файл является временным и сделал, чтобы DeleteOnClose отметил.

using (WebClient myWebClient = new WebClient())
            {
                using (GhostscriptRasterizer rasterizer = new GhostscriptRasterizer())
                {
                    /* custom switches can be added before the file is opened

                    rasterizer.CustomSwitches.Add("-dPrinted");

                    */
                    byte[] buffer = myWebClient.DownloadData(pdfUrl);

                    int bufferSize = 4096;

                    using (var fileStream = System.IO.File.Create("TempPDFolder/" + pdfName, bufferSize, System.IO.FileOptions.DeleteOnClose))
                    {
                        // now use that fileStream to save the pdf stream
                        fileStream.Write(buffer, 0, buffer.Length);
                        rasterizer.Open(fileStream);
                        var image = rasterizer.GetPage(0, 0, 1);

                        var imageURL = "MyCDNpath/Images/" + filename + ".png";

                        _ = UploadFileToS3(image, imageURL);
                    }
                }
            }

Hope это поможет кому-то изо всех сил пытающемуся получить высококачественные изображения от PDF бесплатно.

11
задан Sarah Fordington 7 September 2009 в 13:27
поделиться

2 ответа

Да, вы делаете это безопасный с точки зрения гонки доступ к полю m_LayoutSuspended , однако блокировка требуется по следующей причине, если код выполняет следующие действия:

if (!o.IsLayoutSuspended)  // This is not thread Safe .....
{
  o.SuspendLayout();   // This is not thread Safe, because there's a difference between the checck and the actual write of the variable a race might occur.
  ...
  o.ResumeLayout();
} 

Более безопасный способ, использующий CompareExchange ], чтобы убедиться, что не было условий гонки:

private long m_LayoutSuspended = 0;
public bool SuspendLayout()
{
    return Interlocked.CompareExchange(ref m_LayoutSuspended, 1) == 0;
}

if (o.SuspendLayout()) 
{
  ....
  o.ResumeLayout();
}

Или, еще лучше, просто используйте блокировку.

13
ответ дан 3 December 2019 в 04:52
поделиться

Лично я бы использовал volatile Boolean:

private volatile bool m_LayoutSuspended = false;
public void SuspendLayout()
{
    m_LayoutSuspended = true;
}

public void ResumeLayout()
{
    m_LayoutSuspended = false;
}

public bool IsLayoutSuspended
{
    get { return m_LayoutSuspended; }
}

Опять же, как я недавно признал в другом месте, volatile не означает совсем то, что я думал. Я подозреваю, что это нормально :)

Даже если вы придерживаетесь Interlocked , я бы изменил его на int ... потенциально нет необходимости создавать 32-битные системы изо всех сил пытаются сделать 64-битную запись атомарной, когда они могут легко сделать это с 32-битной ...

10
ответ дан 3 December 2019 в 04:52
поделиться
Другие вопросы по тегам:

Похожие вопросы: